linux/sound/soc/sof/intel/hda.c
<<
>>
Prefs
   1// SPDX-License-Identifier: (GPL-2.0 OR BSD-3-Clause)
   2//
   3// This file is provided under a dual BSD/GPLv2 license.  When using or
   4// redistributing this file, you may do so under either license.
   5//
   6// Copyright(c) 2018 Intel Corporation. All rights reserved.
   7//
   8// Authors: Liam Girdwood <liam.r.girdwood@linux.intel.com>
   9//          Ranjani Sridharan <ranjani.sridharan@linux.intel.com>
  10//          Rander Wang <rander.wang@intel.com>
  11//          Keyon Jie <yang.jie@linux.intel.com>
  12//
  13
  14/*
  15 * Hardware interface for generic Intel audio DSP HDA IP
  16 */
  17
  18#include <sound/hdaudio_ext.h>
  19#include <sound/hda_register.h>
  20
  21#include <linux/module.h>
  22#include <sound/sof.h>
  23#include <sound/sof/xtensa.h>
  24#include "../ops.h"
  25#include "hda.h"
  26#if IS_ENABLED(CONFIG_SND_SOC_SOF_HDA_AUDIO_CODEC)
  27#include "../../codecs/hdac_hda.h"
  28#endif
  29
  30#if IS_ENABLED(CONFIG_SND_SOC_SOF_HDA)
  31#include <sound/soc-acpi-intel-match.h>
  32#endif
  33
  34/* platform specific devices */
  35#include "shim.h"
  36
  37#define IS_CFL(pci) ((pci)->vendor == 0x8086 && (pci)->device == 0xa348)
  38#define IS_CNL(pci) ((pci)->vendor == 0x8086 && (pci)->device == 0x9dc8)
  39
  40/*
  41 * Debug
  42 */
  43
  44struct hda_dsp_msg_code {
  45        u32 code;
  46        const char *msg;
  47};
  48
  49static const struct hda_dsp_msg_code hda_dsp_rom_msg[] = {
  50        {HDA_DSP_ROM_FW_MANIFEST_LOADED, "status: manifest loaded"},
  51        {HDA_DSP_ROM_FW_FW_LOADED, "status: fw loaded"},
  52        {HDA_DSP_ROM_FW_ENTERED, "status: fw entered"},
  53        {HDA_DSP_ROM_CSE_ERROR, "error: cse error"},
  54        {HDA_DSP_ROM_CSE_WRONG_RESPONSE, "error: cse wrong response"},
  55        {HDA_DSP_ROM_IMR_TO_SMALL, "error: IMR too small"},
  56        {HDA_DSP_ROM_BASE_FW_NOT_FOUND, "error: base fw not found"},
  57        {HDA_DSP_ROM_CSE_VALIDATION_FAILED, "error: signature verification failed"},
  58        {HDA_DSP_ROM_IPC_FATAL_ERROR, "error: ipc fatal error"},
  59        {HDA_DSP_ROM_L2_CACHE_ERROR, "error: L2 cache error"},
  60        {HDA_DSP_ROM_LOAD_OFFSET_TO_SMALL, "error: load offset too small"},
  61        {HDA_DSP_ROM_API_PTR_INVALID, "error: API ptr invalid"},
  62        {HDA_DSP_ROM_BASEFW_INCOMPAT, "error: base fw incompatible"},
  63        {HDA_DSP_ROM_UNHANDLED_INTERRUPT, "error: unhandled interrupt"},
  64        {HDA_DSP_ROM_MEMORY_HOLE_ECC, "error: ECC memory hole"},
  65        {HDA_DSP_ROM_KERNEL_EXCEPTION, "error: kernel exception"},
  66        {HDA_DSP_ROM_USER_EXCEPTION, "error: user exception"},
  67        {HDA_DSP_ROM_UNEXPECTED_RESET, "error: unexpected reset"},
  68        {HDA_DSP_ROM_NULL_FW_ENTRY,     "error: null FW entry point"},
  69};
  70
  71static void hda_dsp_get_status_skl(struct snd_sof_dev *sdev)
  72{
  73        u32 status;
  74        int i;
  75
  76        status = snd_sof_dsp_read(sdev, HDA_DSP_BAR,
  77                                  HDA_ADSP_FW_STATUS_SKL);
  78
  79        for (i = 0; i < ARRAY_SIZE(hda_dsp_rom_msg); i++) {
  80                if (status == hda_dsp_rom_msg[i].code) {
  81                        dev_err(sdev->dev, "%s - code %8.8x\n",
  82                                hda_dsp_rom_msg[i].msg, status);
  83                        return;
  84                }
  85        }
  86
  87        /* not for us, must be generic sof message */
  88        dev_dbg(sdev->dev, "unknown ROM status value %8.8x\n", status);
  89}
  90
  91static void hda_dsp_get_status(struct snd_sof_dev *sdev)
  92{
  93        u32 status;
  94        int i;
  95
  96        status = snd_sof_dsp_read(sdev, HDA_DSP_BAR,
  97                                  HDA_DSP_SRAM_REG_ROM_STATUS);
  98
  99        for (i = 0; i < ARRAY_SIZE(hda_dsp_rom_msg); i++) {
 100                if (status == hda_dsp_rom_msg[i].code) {
 101                        dev_err(sdev->dev, "%s - code %8.8x\n",
 102                                hda_dsp_rom_msg[i].msg, status);
 103                        return;
 104                }
 105        }
 106
 107        /* not for us, must be generic sof message */
 108        dev_dbg(sdev->dev, "unknown ROM status value %8.8x\n", status);
 109}
 110
 111static void hda_dsp_get_registers(struct snd_sof_dev *sdev,
 112                                  struct sof_ipc_dsp_oops_xtensa *xoops,
 113                                  struct sof_ipc_panic_info *panic_info,
 114                                  u32 *stack, size_t stack_words)
 115{
 116        u32 offset = sdev->dsp_oops_offset;
 117
 118        /* first read registers */
 119        sof_mailbox_read(sdev, offset, xoops, sizeof(*xoops));
 120
 121        /* note: variable AR register array is not read */
 122
 123        /* then get panic info */
 124        offset += xoops->arch_hdr.totalsize;
 125        sof_block_read(sdev, sdev->mmio_bar, offset,
 126                       panic_info, sizeof(*panic_info));
 127
 128        /* then get the stack */
 129        offset += sizeof(*panic_info);
 130        sof_block_read(sdev, sdev->mmio_bar, offset, stack,
 131                       stack_words * sizeof(u32));
 132}
 133
 134void hda_dsp_dump_skl(struct snd_sof_dev *sdev, u32 flags)
 135{
 136        struct sof_ipc_dsp_oops_xtensa xoops;
 137        struct sof_ipc_panic_info panic_info;
 138        u32 stack[HDA_DSP_STACK_DUMP_SIZE];
 139        u32 status, panic;
 140
 141        /* try APL specific status message types first */
 142        hda_dsp_get_status_skl(sdev);
 143
 144        /* now try generic SOF status messages */
 145        status = snd_sof_dsp_read(sdev, HDA_DSP_BAR,
 146                                  HDA_ADSP_ERROR_CODE_SKL);
 147
 148        /*TODO: Check: there is no define in spec, but it is used in the code*/
 149        panic = snd_sof_dsp_read(sdev, HDA_DSP_BAR,
 150                                 HDA_ADSP_ERROR_CODE_SKL + 0x4);
 151
 152        if (sdev->boot_complete) {
 153                hda_dsp_get_registers(sdev, &xoops, &panic_info, stack,
 154                                      HDA_DSP_STACK_DUMP_SIZE);
 155                snd_sof_get_status(sdev, status, panic, &xoops, &panic_info,
 156                                   stack, HDA_DSP_STACK_DUMP_SIZE);
 157        } else {
 158                dev_err(sdev->dev, "error: status = 0x%8.8x panic = 0x%8.8x\n",
 159                        status, panic);
 160                hda_dsp_get_status_skl(sdev);
 161        }
 162}
 163
 164void hda_dsp_dump(struct snd_sof_dev *sdev, u32 flags)
 165{
 166        struct sof_ipc_dsp_oops_xtensa xoops;
 167        struct sof_ipc_panic_info panic_info;
 168        u32 stack[HDA_DSP_STACK_DUMP_SIZE];
 169        u32 status, panic;
 170
 171        /* try APL specific status message types first */
 172        hda_dsp_get_status(sdev);
 173
 174        /* now try generic SOF status messages */
 175        status = snd_sof_dsp_read(sdev, HDA_DSP_BAR,
 176                                  HDA_DSP_SRAM_REG_FW_STATUS);
 177        panic = snd_sof_dsp_read(sdev, HDA_DSP_BAR, HDA_DSP_SRAM_REG_FW_TRACEP);
 178
 179        if (sdev->boot_complete) {
 180                hda_dsp_get_registers(sdev, &xoops, &panic_info, stack,
 181                                      HDA_DSP_STACK_DUMP_SIZE);
 182                snd_sof_get_status(sdev, status, panic, &xoops, &panic_info,
 183                                   stack, HDA_DSP_STACK_DUMP_SIZE);
 184        } else {
 185                dev_err(sdev->dev, "error: status = 0x%8.8x panic = 0x%8.8x\n",
 186                        status, panic);
 187                hda_dsp_get_status(sdev);
 188        }
 189}
 190
 191void hda_ipc_irq_dump(struct snd_sof_dev *sdev)
 192{
 193        struct hdac_bus *bus = sof_to_bus(sdev);
 194        u32 adspis;
 195        u32 intsts;
 196        u32 intctl;
 197        u32 ppsts;
 198        u8 rirbsts;
 199
 200        /* read key IRQ stats and config registers */
 201        adspis = snd_sof_dsp_read(sdev, HDA_DSP_BAR, HDA_DSP_REG_ADSPIS);
 202        intsts = snd_sof_dsp_read(sdev, HDA_DSP_HDA_BAR, SOF_HDA_INTSTS);
 203        intctl = snd_sof_dsp_read(sdev, HDA_DSP_HDA_BAR, SOF_HDA_INTCTL);
 204        ppsts = snd_sof_dsp_read(sdev, HDA_DSP_PP_BAR, SOF_HDA_REG_PP_PPSTS);
 205        rirbsts = snd_hdac_chip_readb(bus, RIRBSTS);
 206
 207        dev_err(sdev->dev,
 208                "error: hda irq intsts 0x%8.8x intlctl 0x%8.8x rirb %2.2x\n",
 209                intsts, intctl, rirbsts);
 210        dev_err(sdev->dev,
 211                "error: dsp irq ppsts 0x%8.8x adspis 0x%8.8x\n",
 212                ppsts, adspis);
 213}
 214
 215void hda_ipc_dump(struct snd_sof_dev *sdev)
 216{
 217        u32 hipcie;
 218        u32 hipct;
 219        u32 hipcctl;
 220
 221        hda_ipc_irq_dump(sdev);
 222
 223        /* read IPC status */
 224        hipcie = snd_sof_dsp_read(sdev, HDA_DSP_BAR, HDA_DSP_REG_HIPCIE);
 225        hipct = snd_sof_dsp_read(sdev, HDA_DSP_BAR, HDA_DSP_REG_HIPCT);
 226        hipcctl = snd_sof_dsp_read(sdev, HDA_DSP_BAR, HDA_DSP_REG_HIPCCTL);
 227
 228        /* dump the IPC regs */
 229        /* TODO: parse the raw msg */
 230        dev_err(sdev->dev,
 231                "error: host status 0x%8.8x dsp status 0x%8.8x mask 0x%8.8x\n",
 232                hipcie, hipct, hipcctl);
 233}
 234
 235static int hda_init(struct snd_sof_dev *sdev)
 236{
 237        struct hda_bus *hbus;
 238        struct hdac_bus *bus;
 239        struct hdac_ext_bus_ops *ext_ops = NULL;
 240        struct pci_dev *pci = to_pci_dev(sdev->dev);
 241        int ret;
 242
 243        hbus = sof_to_hbus(sdev);
 244        bus = sof_to_bus(sdev);
 245
 246        /* HDA bus init */
 247#if IS_ENABLED(CONFIG_SND_SOC_SOF_HDA_AUDIO_CODEC)
 248        ext_ops = snd_soc_hdac_hda_get_ops();
 249#endif
 250        sof_hda_bus_init(bus, &pci->dev, ext_ops);
 251
 252        /* Workaround for a communication error on CFL (bko#199007) and CNL */
 253        if (IS_CFL(pci) || IS_CNL(pci))
 254                bus->polling_mode = 1;
 255
 256        bus->use_posbuf = 1;
 257        bus->bdl_pos_adj = 0;
 258
 259        mutex_init(&hbus->prepare_mutex);
 260        hbus->pci = pci;
 261        hbus->mixer_assigned = -1;
 262        hbus->modelname = "sofbus";
 263
 264        /* initialise hdac bus */
 265        bus->addr = pci_resource_start(pci, 0);
 266#if IS_ENABLED(CONFIG_PCI)
 267        bus->remap_addr = pci_ioremap_bar(pci, 0);
 268#endif
 269        if (!bus->remap_addr) {
 270                dev_err(bus->dev, "error: ioremap error\n");
 271                return -ENXIO;
 272        }
 273
 274        /* HDA base */
 275        sdev->bar[HDA_DSP_HDA_BAR] = bus->remap_addr;
 276
 277        /* get controller capabilities */
 278        ret = hda_dsp_ctrl_get_caps(sdev);
 279        if (ret < 0)
 280                dev_err(sdev->dev, "error: get caps error\n");
 281
 282        return ret;
 283}
 284
 285#if IS_ENABLED(CONFIG_SND_SOC_SOF_HDA)
 286
 287static const char *fixup_tplg_name(struct snd_sof_dev *sdev,
 288                                   const char *sof_tplg_filename)
 289{
 290        const char *tplg_filename = NULL;
 291        char *filename;
 292        char *split_ext;
 293
 294        filename = devm_kstrdup(sdev->dev, sof_tplg_filename, GFP_KERNEL);
 295        if (!filename)
 296                return NULL;
 297
 298        /* this assumes a .tplg extension */
 299        split_ext = strsep(&filename, ".");
 300        if (split_ext) {
 301                tplg_filename = devm_kasprintf(sdev->dev, GFP_KERNEL,
 302                                               "%s-idisp.tplg", split_ext);
 303                if (!tplg_filename)
 304                        return NULL;
 305        }
 306        return tplg_filename;
 307}
 308
 309#endif
 310
 311static int hda_init_caps(struct snd_sof_dev *sdev)
 312{
 313        struct hdac_bus *bus = sof_to_bus(sdev);
 314#if IS_ENABLED(CONFIG_SND_SOC_SOF_HDA)
 315        struct hdac_ext_link *hlink;
 316        struct snd_soc_acpi_mach_params *mach_params;
 317        struct snd_soc_acpi_mach *hda_mach;
 318        struct snd_sof_pdata *pdata = sdev->pdata;
 319        struct snd_soc_acpi_mach *mach;
 320        const char *tplg_filename;
 321        int codec_num = 0;
 322        int i;
 323#endif
 324        int ret = 0;
 325
 326        device_disable_async_suspend(bus->dev);
 327
 328        /* check if dsp is there */
 329        if (bus->ppcap)
 330                dev_dbg(sdev->dev, "PP capability, will probe DSP later.\n");
 331
 332        ret = hda_dsp_ctrl_init_chip(sdev, true);
 333        if (ret < 0) {
 334                dev_err(bus->dev, "error: init chip failed with ret: %d\n",
 335                        ret);
 336                return ret;
 337        }
 338
 339#if IS_ENABLED(CONFIG_SND_SOC_SOF_HDA)
 340        if (bus->mlcap)
 341                snd_hdac_ext_bus_get_ml_capabilities(bus);
 342
 343        /* init i915 and HDMI codecs */
 344        ret = hda_codec_i915_init(sdev);
 345        if (ret < 0) {
 346                dev_err(sdev->dev, "error: no HDMI audio devices found\n");
 347                return ret;
 348        }
 349
 350        /* codec detection */
 351        if (!bus->codec_mask) {
 352                dev_info(bus->dev, "no hda codecs found!\n");
 353        } else {
 354                dev_info(bus->dev, "hda codecs found, mask %lx\n",
 355                         bus->codec_mask);
 356
 357                for (i = 0; i < HDA_MAX_CODECS; i++) {
 358                        if (bus->codec_mask & (1 << i))
 359                                codec_num++;
 360                }
 361
 362                /*
 363                 * If no machine driver is found, then:
 364                 *
 365                 * hda machine driver is used if :
 366                 * 1. there is one HDMI codec and one external HDAudio codec
 367                 * 2. only HDMI codec
 368                 */
 369                if (!pdata->machine && codec_num <= 2 &&
 370                    HDA_IDISP_CODEC(bus->codec_mask)) {
 371                        hda_mach = snd_soc_acpi_intel_hda_machines;
 372                        pdata->machine = hda_mach;
 373
 374                        /* topology: use the info from hda_machines */
 375                        pdata->tplg_filename =
 376                                hda_mach->sof_tplg_filename;
 377
 378                        /* firmware: pick the first in machine list */
 379                        mach = pdata->desc->machines;
 380                        pdata->fw_filename = mach->sof_fw_filename;
 381
 382                        dev_info(bus->dev, "using HDA machine driver %s now\n",
 383                                 hda_mach->drv_name);
 384
 385                        /* fixup topology file for HDMI only platforms */
 386                        if (codec_num == 1) {
 387                                /* use local variable for readability */
 388                                tplg_filename = pdata->tplg_filename;
 389                                tplg_filename = fixup_tplg_name(sdev, tplg_filename);
 390                                if (!tplg_filename) {
 391                                        hda_codec_i915_exit(sdev);
 392                                        return ret;
 393                                }
 394                                pdata->tplg_filename = tplg_filename;
 395                        }
 396                }
 397        }
 398
 399        /* used by hda machine driver to create dai links */
 400        if (pdata->machine) {
 401                mach_params = (struct snd_soc_acpi_mach_params *)
 402                        &pdata->machine->mach_params;
 403                mach_params->codec_mask = bus->codec_mask;
 404                mach_params->platform = dev_name(sdev->dev);
 405        }
 406
 407        /* create codec instances */
 408        hda_codec_probe_bus(sdev);
 409
 410        hda_codec_i915_put(sdev);
 411
 412        /*
 413         * we are done probing so decrement link counts
 414         */
 415        list_for_each_entry(hlink, &bus->hlink_list, list)
 416                snd_hdac_ext_bus_link_put(bus, hlink);
 417#endif
 418        return 0;
 419}
 420
 421static const struct sof_intel_dsp_desc
 422        *get_chip_info(struct snd_sof_pdata *pdata)
 423{
 424        const struct sof_dev_desc *desc = pdata->desc;
 425        const struct sof_intel_dsp_desc *chip_info;
 426
 427        chip_info = desc->chip_info;
 428
 429        return chip_info;
 430}
 431
 432int hda_dsp_probe(struct snd_sof_dev *sdev)
 433{
 434        struct pci_dev *pci = to_pci_dev(sdev->dev);
 435        struct sof_intel_hda_dev *hdev;
 436        struct hdac_bus *bus;
 437        const struct sof_intel_dsp_desc *chip;
 438        int ret = 0;
 439
 440        /*
 441         * detect DSP by checking class/subclass/prog-id information
 442         * class=04 subclass 03 prog-if 00: no DSP, legacy driver is required
 443         * class=04 subclass 01 prog-if 00: DSP is present
 444         *   (and may be required e.g. for DMIC or SSP support)
 445         * class=04 subclass 03 prog-if 80: either of DSP or legacy mode works
 446         */
 447        if (pci->class == 0x040300) {
 448                dev_err(sdev->dev, "error: the DSP is not enabled on this platform, aborting probe\n");
 449                return -ENODEV;
 450        } else if (pci->class != 0x040100 && pci->class != 0x040380) {
 451                dev_err(sdev->dev, "error: unknown PCI class/subclass/prog-if 0x%06x found, aborting probe\n", pci->class);
 452                return -ENODEV;
 453        }
 454        dev_info(sdev->dev, "DSP detected with PCI class/subclass/prog-if 0x%06x\n", pci->class);
 455
 456        chip = get_chip_info(sdev->pdata);
 457        if (!chip) {
 458                dev_err(sdev->dev, "error: no such device supported, chip id:%x\n",
 459                        pci->device);
 460                ret = -EIO;
 461                goto err;
 462        }
 463
 464        hdev = devm_kzalloc(sdev->dev, sizeof(*hdev), GFP_KERNEL);
 465        if (!hdev)
 466                return -ENOMEM;
 467        sdev->pdata->hw_pdata = hdev;
 468        hdev->desc = chip;
 469
 470        hdev->dmic_dev = platform_device_register_data(sdev->dev, "dmic-codec",
 471                                                       PLATFORM_DEVID_NONE,
 472                                                       NULL, 0);
 473        if (IS_ERR(hdev->dmic_dev)) {
 474                dev_err(sdev->dev, "error: failed to create DMIC device\n");
 475                return PTR_ERR(hdev->dmic_dev);
 476        }
 477
 478        /*
 479         * use position update IPC if either it is forced
 480         * or we don't have other choice
 481         */
 482#if IS_ENABLED(CONFIG_SND_SOC_SOF_DEBUG_FORCE_IPC_POSITION)
 483        hdev->no_ipc_position = 0;
 484#else
 485        hdev->no_ipc_position = sof_ops(sdev)->pcm_pointer ? 1 : 0;
 486#endif
 487
 488        /* set up HDA base */
 489        bus = sof_to_bus(sdev);
 490        ret = hda_init(sdev);
 491        if (ret < 0)
 492                goto hdac_bus_unmap;
 493
 494        /* DSP base */
 495#if IS_ENABLED(CONFIG_PCI)
 496        sdev->bar[HDA_DSP_BAR] = pci_ioremap_bar(pci, HDA_DSP_BAR);
 497#endif
 498        if (!sdev->bar[HDA_DSP_BAR]) {
 499                dev_err(sdev->dev, "error: ioremap error\n");
 500                ret = -ENXIO;
 501                goto hdac_bus_unmap;
 502        }
 503
 504        sdev->mmio_bar = HDA_DSP_BAR;
 505        sdev->mailbox_bar = HDA_DSP_BAR;
 506
 507        /* allow 64bit DMA address if supported by H/W */
 508        if (!dma_set_mask(&pci->dev, DMA_BIT_MASK(64))) {
 509                dev_dbg(sdev->dev, "DMA mask is 64 bit\n");
 510                dma_set_coherent_mask(&pci->dev, DMA_BIT_MASK(64));
 511        } else {
 512                dev_dbg(sdev->dev, "DMA mask is 32 bit\n");
 513                dma_set_mask(&pci->dev, DMA_BIT_MASK(32));
 514                dma_set_coherent_mask(&pci->dev, DMA_BIT_MASK(32));
 515        }
 516
 517        /* init streams */
 518        ret = hda_dsp_stream_init(sdev);
 519        if (ret < 0) {
 520                dev_err(sdev->dev, "error: failed to init streams\n");
 521                /*
 522                 * not all errors are due to memory issues, but trying
 523                 * to free everything does not harm
 524                 */
 525                goto free_streams;
 526        }
 527
 528        /*
 529         * register our IRQ
 530         * let's try to enable msi firstly
 531         * if it fails, use legacy interrupt mode
 532         * TODO: support interrupt mode selection with kernel parameter
 533         *       support msi multiple vectors
 534         */
 535        ret = pci_alloc_irq_vectors(pci, 1, 1, PCI_IRQ_MSI);
 536        if (ret < 0) {
 537                dev_info(sdev->dev, "use legacy interrupt mode\n");
 538                /*
 539                 * in IO-APIC mode, hda->irq and ipc_irq are using the same
 540                 * irq number of pci->irq
 541                 */
 542                hdev->irq = pci->irq;
 543                sdev->ipc_irq = pci->irq;
 544                sdev->msi_enabled = 0;
 545        } else {
 546                dev_info(sdev->dev, "use msi interrupt mode\n");
 547                hdev->irq = pci_irq_vector(pci, 0);
 548                /* ipc irq number is the same of hda irq */
 549                sdev->ipc_irq = hdev->irq;
 550                sdev->msi_enabled = 1;
 551        }
 552
 553        dev_dbg(sdev->dev, "using HDA IRQ %d\n", hdev->irq);
 554        ret = request_threaded_irq(hdev->irq, hda_dsp_stream_interrupt,
 555                                   hda_dsp_stream_threaded_handler,
 556                                   IRQF_SHARED, "AudioHDA", bus);
 557        if (ret < 0) {
 558                dev_err(sdev->dev, "error: failed to register HDA IRQ %d\n",
 559                        hdev->irq);
 560                goto free_irq_vector;
 561        }
 562
 563        dev_dbg(sdev->dev, "using IPC IRQ %d\n", sdev->ipc_irq);
 564        ret = request_threaded_irq(sdev->ipc_irq, hda_dsp_ipc_irq_handler,
 565                                   sof_ops(sdev)->irq_thread, IRQF_SHARED,
 566                                   "AudioDSP", sdev);
 567        if (ret < 0) {
 568                dev_err(sdev->dev, "error: failed to register IPC IRQ %d\n",
 569                        sdev->ipc_irq);
 570                goto free_hda_irq;
 571        }
 572
 573        pci_set_master(pci);
 574        synchronize_irq(pci->irq);
 575
 576        /*
 577         * clear TCSEL to clear playback on some HD Audio
 578         * codecs. PCI TCSEL is defined in the Intel manuals.
 579         */
 580        snd_sof_pci_update_bits(sdev, PCI_TCSEL, 0x07, 0);
 581
 582        /* init HDA capabilities */
 583        ret = hda_init_caps(sdev);
 584        if (ret < 0)
 585                goto free_ipc_irq;
 586
 587        /* enable ppcap interrupt */
 588        hda_dsp_ctrl_ppcap_enable(sdev, true);
 589        hda_dsp_ctrl_ppcap_int_enable(sdev, true);
 590
 591        /* initialize waitq for code loading */
 592        init_waitqueue_head(&sdev->waitq);
 593
 594        /* set default mailbox offset for FW ready message */
 595        sdev->dsp_box.offset = HDA_DSP_MBOX_UPLINK_OFFSET;
 596
 597        return 0;
 598
 599free_ipc_irq:
 600        free_irq(sdev->ipc_irq, sdev);
 601free_hda_irq:
 602        free_irq(hdev->irq, bus);
 603free_irq_vector:
 604        if (sdev->msi_enabled)
 605                pci_free_irq_vectors(pci);
 606free_streams:
 607        hda_dsp_stream_free(sdev);
 608/* dsp_unmap: not currently used */
 609        iounmap(sdev->bar[HDA_DSP_BAR]);
 610hdac_bus_unmap:
 611        iounmap(bus->remap_addr);
 612err:
 613        return ret;
 614}
 615
 616int hda_dsp_remove(struct snd_sof_dev *sdev)
 617{
 618        struct sof_intel_hda_dev *hda = sdev->pdata->hw_pdata;
 619        struct hdac_bus *bus = sof_to_bus(sdev);
 620        struct pci_dev *pci = to_pci_dev(sdev->dev);
 621        const struct sof_intel_dsp_desc *chip = hda->desc;
 622
 623#if IS_ENABLED(CONFIG_SND_SOC_SOF_HDA)
 624        /* codec removal, invoke bus_device_remove */
 625        snd_hdac_ext_bus_device_remove(bus);
 626#endif
 627
 628        if (!IS_ERR_OR_NULL(hda->dmic_dev))
 629                platform_device_unregister(hda->dmic_dev);
 630
 631        /* disable DSP IRQ */
 632        snd_sof_dsp_update_bits(sdev, HDA_DSP_PP_BAR, SOF_HDA_REG_PP_PPCTL,
 633                                SOF_HDA_PPCTL_PIE, 0);
 634
 635        /* disable CIE and GIE interrupts */
 636        snd_sof_dsp_update_bits(sdev, HDA_DSP_HDA_BAR, SOF_HDA_INTCTL,
 637                                SOF_HDA_INT_CTRL_EN | SOF_HDA_INT_GLOBAL_EN, 0);
 638
 639        /* disable cores */
 640        if (chip)
 641                hda_dsp_core_reset_power_down(sdev, chip->cores_mask);
 642
 643        /* disable DSP */
 644        snd_sof_dsp_update_bits(sdev, HDA_DSP_PP_BAR, SOF_HDA_REG_PP_PPCTL,
 645                                SOF_HDA_PPCTL_GPROCEN, 0);
 646
 647        free_irq(sdev->ipc_irq, sdev);
 648        free_irq(hda->irq, bus);
 649        if (sdev->msi_enabled)
 650                pci_free_irq_vectors(pci);
 651
 652        hda_dsp_stream_free(sdev);
 653#if IS_ENABLED(CONFIG_SND_SOC_SOF_HDA)
 654        snd_hdac_link_free_all(bus);
 655#endif
 656
 657        iounmap(sdev->bar[HDA_DSP_BAR]);
 658        iounmap(bus->remap_addr);
 659
 660#if IS_ENABLED(CONFIG_SND_SOC_SOF_HDA)
 661        snd_hdac_ext_bus_exit(bus);
 662#endif
 663        hda_codec_i915_exit(sdev);
 664
 665        return 0;
 666}
 667
 668MODULE_LICENSE("Dual BSD/GPL");
 669