cachepc-linux

Fork of AMDESE/linux with modifications for CachePC side-channel attack
git clone https://git.sinitax.com/sinitax/cachepc-linux
Log | Files | Refs | README | LICENSE | sfeed.txt

qcom_q6v5_pas.c (22154B)


      1// SPDX-License-Identifier: GPL-2.0-only
      2/*
      3 * Qualcomm ADSP/SLPI Peripheral Image Loader for MSM8974 and MSM8996
      4 *
      5 * Copyright (C) 2016 Linaro Ltd
      6 * Copyright (C) 2014 Sony Mobile Communications AB
      7 * Copyright (c) 2012-2013, The Linux Foundation. All rights reserved.
      8 */
      9
     10#include <linux/clk.h>
     11#include <linux/firmware.h>
     12#include <linux/interrupt.h>
     13#include <linux/kernel.h>
     14#include <linux/module.h>
     15#include <linux/of_address.h>
     16#include <linux/of_device.h>
     17#include <linux/platform_device.h>
     18#include <linux/pm_domain.h>
     19#include <linux/pm_runtime.h>
     20#include <linux/qcom_scm.h>
     21#include <linux/regulator/consumer.h>
     22#include <linux/remoteproc.h>
     23#include <linux/soc/qcom/mdt_loader.h>
     24#include <linux/soc/qcom/smem.h>
     25#include <linux/soc/qcom/smem_state.h>
     26
     27#include "qcom_common.h"
     28#include "qcom_pil_info.h"
     29#include "qcom_q6v5.h"
     30#include "remoteproc_internal.h"
     31
     32struct adsp_data {
     33	int crash_reason_smem;
     34	const char *firmware_name;
     35	int pas_id;
     36	unsigned int minidump_id;
     37	bool has_aggre2_clk;
     38	bool auto_boot;
     39
     40	char **proxy_pd_names;
     41
     42	const char *load_state;
     43	const char *ssr_name;
     44	const char *sysmon_name;
     45	int ssctl_id;
     46};
     47
     48struct qcom_adsp {
     49	struct device *dev;
     50	struct rproc *rproc;
     51
     52	struct qcom_q6v5 q6v5;
     53
     54	struct clk *xo;
     55	struct clk *aggre2_clk;
     56
     57	struct regulator *cx_supply;
     58	struct regulator *px_supply;
     59
     60	struct device *proxy_pds[3];
     61
     62	int proxy_pd_count;
     63
     64	int pas_id;
     65	unsigned int minidump_id;
     66	int crash_reason_smem;
     67	bool has_aggre2_clk;
     68	const char *info_name;
     69
     70	struct completion start_done;
     71	struct completion stop_done;
     72
     73	phys_addr_t mem_phys;
     74	phys_addr_t mem_reloc;
     75	void *mem_region;
     76	size_t mem_size;
     77
     78	struct qcom_rproc_glink glink_subdev;
     79	struct qcom_rproc_subdev smd_subdev;
     80	struct qcom_rproc_ssr ssr_subdev;
     81	struct qcom_sysmon *sysmon;
     82
     83	struct qcom_scm_pas_metadata pas_metadata;
     84};
     85
     86static void adsp_minidump(struct rproc *rproc)
     87{
     88	struct qcom_adsp *adsp = rproc->priv;
     89
     90	qcom_minidump(rproc, adsp->minidump_id);
     91}
     92
     93static int adsp_pds_enable(struct qcom_adsp *adsp, struct device **pds,
     94			   size_t pd_count)
     95{
     96	int ret;
     97	int i;
     98
     99	for (i = 0; i < pd_count; i++) {
    100		dev_pm_genpd_set_performance_state(pds[i], INT_MAX);
    101		ret = pm_runtime_get_sync(pds[i]);
    102		if (ret < 0) {
    103			pm_runtime_put_noidle(pds[i]);
    104			dev_pm_genpd_set_performance_state(pds[i], 0);
    105			goto unroll_pd_votes;
    106		}
    107	}
    108
    109	return 0;
    110
    111unroll_pd_votes:
    112	for (i--; i >= 0; i--) {
    113		dev_pm_genpd_set_performance_state(pds[i], 0);
    114		pm_runtime_put(pds[i]);
    115	}
    116
    117	return ret;
    118};
    119
    120static void adsp_pds_disable(struct qcom_adsp *adsp, struct device **pds,
    121			     size_t pd_count)
    122{
    123	int i;
    124
    125	for (i = 0; i < pd_count; i++) {
    126		dev_pm_genpd_set_performance_state(pds[i], 0);
    127		pm_runtime_put(pds[i]);
    128	}
    129}
    130
    131static int adsp_unprepare(struct rproc *rproc)
    132{
    133	struct qcom_adsp *adsp = (struct qcom_adsp *)rproc->priv;
    134
    135	/*
    136	 * adsp_load() did pass pas_metadata to the SCM driver for storing
    137	 * metadata context. It might have been released already if
    138	 * auth_and_reset() was successful, but in other cases clean it up
    139	 * here.
    140	 */
    141	qcom_scm_pas_metadata_release(&adsp->pas_metadata);
    142
    143	return 0;
    144}
    145
    146static int adsp_load(struct rproc *rproc, const struct firmware *fw)
    147{
    148	struct qcom_adsp *adsp = (struct qcom_adsp *)rproc->priv;
    149	int ret;
    150
    151	ret = qcom_mdt_pas_init(adsp->dev, fw, rproc->firmware, adsp->pas_id,
    152				adsp->mem_phys, &adsp->pas_metadata);
    153	if (ret)
    154		return ret;
    155
    156	ret = qcom_mdt_load_no_init(adsp->dev, fw, rproc->firmware, adsp->pas_id,
    157				    adsp->mem_region, adsp->mem_phys, adsp->mem_size,
    158				    &adsp->mem_reloc);
    159	if (ret)
    160		return ret;
    161
    162	qcom_pil_info_store(adsp->info_name, adsp->mem_phys, adsp->mem_size);
    163
    164	return 0;
    165}
    166
    167static int adsp_start(struct rproc *rproc)
    168{
    169	struct qcom_adsp *adsp = (struct qcom_adsp *)rproc->priv;
    170	int ret;
    171
    172	ret = qcom_q6v5_prepare(&adsp->q6v5);
    173	if (ret)
    174		return ret;
    175
    176	ret = adsp_pds_enable(adsp, adsp->proxy_pds, adsp->proxy_pd_count);
    177	if (ret < 0)
    178		goto disable_irqs;
    179
    180	ret = clk_prepare_enable(adsp->xo);
    181	if (ret)
    182		goto disable_proxy_pds;
    183
    184	ret = clk_prepare_enable(adsp->aggre2_clk);
    185	if (ret)
    186		goto disable_xo_clk;
    187
    188	ret = regulator_enable(adsp->cx_supply);
    189	if (ret)
    190		goto disable_aggre2_clk;
    191
    192	ret = regulator_enable(adsp->px_supply);
    193	if (ret)
    194		goto disable_cx_supply;
    195
    196	ret = qcom_scm_pas_auth_and_reset(adsp->pas_id);
    197	if (ret) {
    198		dev_err(adsp->dev,
    199			"failed to authenticate image and release reset\n");
    200		goto disable_px_supply;
    201	}
    202
    203	ret = qcom_q6v5_wait_for_start(&adsp->q6v5, msecs_to_jiffies(5000));
    204	if (ret == -ETIMEDOUT) {
    205		dev_err(adsp->dev, "start timed out\n");
    206		qcom_scm_pas_shutdown(adsp->pas_id);
    207		goto disable_px_supply;
    208	}
    209
    210	qcom_scm_pas_metadata_release(&adsp->pas_metadata);
    211
    212	return 0;
    213
    214disable_px_supply:
    215	regulator_disable(adsp->px_supply);
    216disable_cx_supply:
    217	regulator_disable(adsp->cx_supply);
    218disable_aggre2_clk:
    219	clk_disable_unprepare(adsp->aggre2_clk);
    220disable_xo_clk:
    221	clk_disable_unprepare(adsp->xo);
    222disable_proxy_pds:
    223	adsp_pds_disable(adsp, adsp->proxy_pds, adsp->proxy_pd_count);
    224disable_irqs:
    225	qcom_q6v5_unprepare(&adsp->q6v5);
    226
    227	return ret;
    228}
    229
    230static void qcom_pas_handover(struct qcom_q6v5 *q6v5)
    231{
    232	struct qcom_adsp *adsp = container_of(q6v5, struct qcom_adsp, q6v5);
    233
    234	regulator_disable(adsp->px_supply);
    235	regulator_disable(adsp->cx_supply);
    236	clk_disable_unprepare(adsp->aggre2_clk);
    237	clk_disable_unprepare(adsp->xo);
    238	adsp_pds_disable(adsp, adsp->proxy_pds, adsp->proxy_pd_count);
    239}
    240
    241static int adsp_stop(struct rproc *rproc)
    242{
    243	struct qcom_adsp *adsp = (struct qcom_adsp *)rproc->priv;
    244	int handover;
    245	int ret;
    246
    247	ret = qcom_q6v5_request_stop(&adsp->q6v5, adsp->sysmon);
    248	if (ret == -ETIMEDOUT)
    249		dev_err(adsp->dev, "timed out on wait\n");
    250
    251	ret = qcom_scm_pas_shutdown(adsp->pas_id);
    252	if (ret)
    253		dev_err(adsp->dev, "failed to shutdown: %d\n", ret);
    254
    255	handover = qcom_q6v5_unprepare(&adsp->q6v5);
    256	if (handover)
    257		qcom_pas_handover(&adsp->q6v5);
    258
    259	return ret;
    260}
    261
    262static void *adsp_da_to_va(struct rproc *rproc, u64 da, size_t len, bool *is_iomem)
    263{
    264	struct qcom_adsp *adsp = (struct qcom_adsp *)rproc->priv;
    265	int offset;
    266
    267	offset = da - adsp->mem_reloc;
    268	if (offset < 0 || offset + len > adsp->mem_size)
    269		return NULL;
    270
    271	return adsp->mem_region + offset;
    272}
    273
    274static unsigned long adsp_panic(struct rproc *rproc)
    275{
    276	struct qcom_adsp *adsp = (struct qcom_adsp *)rproc->priv;
    277
    278	return qcom_q6v5_panic(&adsp->q6v5);
    279}
    280
    281static const struct rproc_ops adsp_ops = {
    282	.unprepare = adsp_unprepare,
    283	.start = adsp_start,
    284	.stop = adsp_stop,
    285	.da_to_va = adsp_da_to_va,
    286	.parse_fw = qcom_register_dump_segments,
    287	.load = adsp_load,
    288	.panic = adsp_panic,
    289};
    290
    291static const struct rproc_ops adsp_minidump_ops = {
    292	.unprepare = adsp_unprepare,
    293	.start = adsp_start,
    294	.stop = adsp_stop,
    295	.da_to_va = adsp_da_to_va,
    296	.load = adsp_load,
    297	.panic = adsp_panic,
    298	.coredump = adsp_minidump,
    299};
    300
    301static int adsp_init_clock(struct qcom_adsp *adsp)
    302{
    303	int ret;
    304
    305	adsp->xo = devm_clk_get(adsp->dev, "xo");
    306	if (IS_ERR(adsp->xo)) {
    307		ret = PTR_ERR(adsp->xo);
    308		if (ret != -EPROBE_DEFER)
    309			dev_err(adsp->dev, "failed to get xo clock");
    310		return ret;
    311	}
    312
    313	if (adsp->has_aggre2_clk) {
    314		adsp->aggre2_clk = devm_clk_get(adsp->dev, "aggre2");
    315		if (IS_ERR(adsp->aggre2_clk)) {
    316			ret = PTR_ERR(adsp->aggre2_clk);
    317			if (ret != -EPROBE_DEFER)
    318				dev_err(adsp->dev,
    319					"failed to get aggre2 clock");
    320			return ret;
    321		}
    322	}
    323
    324	return 0;
    325}
    326
    327static int adsp_init_regulator(struct qcom_adsp *adsp)
    328{
    329	adsp->cx_supply = devm_regulator_get(adsp->dev, "cx");
    330	if (IS_ERR(adsp->cx_supply))
    331		return PTR_ERR(adsp->cx_supply);
    332
    333	regulator_set_load(adsp->cx_supply, 100000);
    334
    335	adsp->px_supply = devm_regulator_get(adsp->dev, "px");
    336	return PTR_ERR_OR_ZERO(adsp->px_supply);
    337}
    338
    339static int adsp_pds_attach(struct device *dev, struct device **devs,
    340			   char **pd_names)
    341{
    342	size_t num_pds = 0;
    343	int ret;
    344	int i;
    345
    346	if (!pd_names)
    347		return 0;
    348
    349	/* Handle single power domain */
    350	if (dev->pm_domain) {
    351		devs[0] = dev;
    352		pm_runtime_enable(dev);
    353		return 1;
    354	}
    355
    356	while (pd_names[num_pds])
    357		num_pds++;
    358
    359	for (i = 0; i < num_pds; i++) {
    360		devs[i] = dev_pm_domain_attach_by_name(dev, pd_names[i]);
    361		if (IS_ERR_OR_NULL(devs[i])) {
    362			ret = PTR_ERR(devs[i]) ? : -ENODATA;
    363			goto unroll_attach;
    364		}
    365	}
    366
    367	return num_pds;
    368
    369unroll_attach:
    370	for (i--; i >= 0; i--)
    371		dev_pm_domain_detach(devs[i], false);
    372
    373	return ret;
    374};
    375
    376static void adsp_pds_detach(struct qcom_adsp *adsp, struct device **pds,
    377			    size_t pd_count)
    378{
    379	struct device *dev = adsp->dev;
    380	int i;
    381
    382	/* Handle single power domain */
    383	if (dev->pm_domain && pd_count) {
    384		pm_runtime_disable(dev);
    385		return;
    386	}
    387
    388	for (i = 0; i < pd_count; i++)
    389		dev_pm_domain_detach(pds[i], false);
    390}
    391
    392static int adsp_alloc_memory_region(struct qcom_adsp *adsp)
    393{
    394	struct device_node *node;
    395	struct resource r;
    396	int ret;
    397
    398	node = of_parse_phandle(adsp->dev->of_node, "memory-region", 0);
    399	if (!node) {
    400		dev_err(adsp->dev, "no memory-region specified\n");
    401		return -EINVAL;
    402	}
    403
    404	ret = of_address_to_resource(node, 0, &r);
    405	if (ret)
    406		return ret;
    407
    408	adsp->mem_phys = adsp->mem_reloc = r.start;
    409	adsp->mem_size = resource_size(&r);
    410	adsp->mem_region = devm_ioremap_wc(adsp->dev, adsp->mem_phys, adsp->mem_size);
    411	if (!adsp->mem_region) {
    412		dev_err(adsp->dev, "unable to map memory region: %pa+%zx\n",
    413			&r.start, adsp->mem_size);
    414		return -EBUSY;
    415	}
    416
    417	return 0;
    418}
    419
    420static int adsp_probe(struct platform_device *pdev)
    421{
    422	const struct adsp_data *desc;
    423	struct qcom_adsp *adsp;
    424	struct rproc *rproc;
    425	const char *fw_name;
    426	const struct rproc_ops *ops = &adsp_ops;
    427	int ret;
    428
    429	desc = of_device_get_match_data(&pdev->dev);
    430	if (!desc)
    431		return -EINVAL;
    432
    433	if (!qcom_scm_is_available())
    434		return -EPROBE_DEFER;
    435
    436	fw_name = desc->firmware_name;
    437	ret = of_property_read_string(pdev->dev.of_node, "firmware-name",
    438				      &fw_name);
    439	if (ret < 0 && ret != -EINVAL)
    440		return ret;
    441
    442	if (desc->minidump_id)
    443		ops = &adsp_minidump_ops;
    444
    445	rproc = rproc_alloc(&pdev->dev, pdev->name, ops, fw_name, sizeof(*adsp));
    446
    447	if (!rproc) {
    448		dev_err(&pdev->dev, "unable to allocate remoteproc\n");
    449		return -ENOMEM;
    450	}
    451
    452	rproc->auto_boot = desc->auto_boot;
    453	rproc_coredump_set_elf_info(rproc, ELFCLASS32, EM_NONE);
    454
    455	adsp = (struct qcom_adsp *)rproc->priv;
    456	adsp->dev = &pdev->dev;
    457	adsp->rproc = rproc;
    458	adsp->minidump_id = desc->minidump_id;
    459	adsp->pas_id = desc->pas_id;
    460	adsp->has_aggre2_clk = desc->has_aggre2_clk;
    461	adsp->info_name = desc->sysmon_name;
    462	platform_set_drvdata(pdev, adsp);
    463
    464	device_wakeup_enable(adsp->dev);
    465
    466	ret = adsp_alloc_memory_region(adsp);
    467	if (ret)
    468		goto free_rproc;
    469
    470	ret = adsp_init_clock(adsp);
    471	if (ret)
    472		goto free_rproc;
    473
    474	ret = adsp_init_regulator(adsp);
    475	if (ret)
    476		goto free_rproc;
    477
    478	ret = adsp_pds_attach(&pdev->dev, adsp->proxy_pds,
    479			      desc->proxy_pd_names);
    480	if (ret < 0)
    481		goto free_rproc;
    482	adsp->proxy_pd_count = ret;
    483
    484	ret = qcom_q6v5_init(&adsp->q6v5, pdev, rproc, desc->crash_reason_smem, desc->load_state,
    485			     qcom_pas_handover);
    486	if (ret)
    487		goto detach_proxy_pds;
    488
    489	qcom_add_glink_subdev(rproc, &adsp->glink_subdev, desc->ssr_name);
    490	qcom_add_smd_subdev(rproc, &adsp->smd_subdev);
    491	qcom_add_ssr_subdev(rproc, &adsp->ssr_subdev, desc->ssr_name);
    492	adsp->sysmon = qcom_add_sysmon_subdev(rproc,
    493					      desc->sysmon_name,
    494					      desc->ssctl_id);
    495	if (IS_ERR(adsp->sysmon)) {
    496		ret = PTR_ERR(adsp->sysmon);
    497		goto detach_proxy_pds;
    498	}
    499
    500	ret = rproc_add(rproc);
    501	if (ret)
    502		goto detach_proxy_pds;
    503
    504	return 0;
    505
    506detach_proxy_pds:
    507	adsp_pds_detach(adsp, adsp->proxy_pds, adsp->proxy_pd_count);
    508free_rproc:
    509	rproc_free(rproc);
    510
    511	return ret;
    512}
    513
    514static int adsp_remove(struct platform_device *pdev)
    515{
    516	struct qcom_adsp *adsp = platform_get_drvdata(pdev);
    517
    518	rproc_del(adsp->rproc);
    519
    520	qcom_q6v5_deinit(&adsp->q6v5);
    521	qcom_remove_glink_subdev(adsp->rproc, &adsp->glink_subdev);
    522	qcom_remove_sysmon_subdev(adsp->sysmon);
    523	qcom_remove_smd_subdev(adsp->rproc, &adsp->smd_subdev);
    524	qcom_remove_ssr_subdev(adsp->rproc, &adsp->ssr_subdev);
    525	rproc_free(adsp->rproc);
    526
    527	return 0;
    528}
    529
    530static const struct adsp_data adsp_resource_init = {
    531		.crash_reason_smem = 423,
    532		.firmware_name = "adsp.mdt",
    533		.pas_id = 1,
    534		.has_aggre2_clk = false,
    535		.auto_boot = true,
    536		.ssr_name = "lpass",
    537		.sysmon_name = "adsp",
    538		.ssctl_id = 0x14,
    539};
    540
    541static const struct adsp_data sdm845_adsp_resource_init = {
    542		.crash_reason_smem = 423,
    543		.firmware_name = "adsp.mdt",
    544		.pas_id = 1,
    545		.has_aggre2_clk = false,
    546		.auto_boot = true,
    547		.load_state = "adsp",
    548		.ssr_name = "lpass",
    549		.sysmon_name = "adsp",
    550		.ssctl_id = 0x14,
    551};
    552
    553static const struct adsp_data sm6350_adsp_resource = {
    554	.crash_reason_smem = 423,
    555	.firmware_name = "adsp.mdt",
    556	.pas_id = 1,
    557	.has_aggre2_clk = false,
    558	.auto_boot = true,
    559	.proxy_pd_names = (char*[]){
    560		"lcx",
    561		"lmx",
    562		NULL
    563	},
    564	.load_state = "adsp",
    565	.ssr_name = "lpass",
    566	.sysmon_name = "adsp",
    567	.ssctl_id = 0x14,
    568};
    569
    570static const struct adsp_data sm8150_adsp_resource = {
    571		.crash_reason_smem = 423,
    572		.firmware_name = "adsp.mdt",
    573		.pas_id = 1,
    574		.has_aggre2_clk = false,
    575		.auto_boot = true,
    576		.proxy_pd_names = (char*[]){
    577			"cx",
    578			NULL
    579		},
    580		.load_state = "adsp",
    581		.ssr_name = "lpass",
    582		.sysmon_name = "adsp",
    583		.ssctl_id = 0x14,
    584};
    585
    586static const struct adsp_data sm8250_adsp_resource = {
    587	.crash_reason_smem = 423,
    588	.firmware_name = "adsp.mdt",
    589	.pas_id = 1,
    590	.has_aggre2_clk = false,
    591	.auto_boot = true,
    592	.proxy_pd_names = (char*[]){
    593		"lcx",
    594		"lmx",
    595		NULL
    596	},
    597	.load_state = "adsp",
    598	.ssr_name = "lpass",
    599	.sysmon_name = "adsp",
    600	.ssctl_id = 0x14,
    601};
    602
    603static const struct adsp_data sm8350_adsp_resource = {
    604	.crash_reason_smem = 423,
    605	.firmware_name = "adsp.mdt",
    606	.pas_id = 1,
    607	.has_aggre2_clk = false,
    608	.auto_boot = true,
    609	.proxy_pd_names = (char*[]){
    610		"lcx",
    611		"lmx",
    612		NULL
    613	},
    614	.load_state = "adsp",
    615	.ssr_name = "lpass",
    616	.sysmon_name = "adsp",
    617	.ssctl_id = 0x14,
    618};
    619
    620static const struct adsp_data msm8996_adsp_resource = {
    621		.crash_reason_smem = 423,
    622		.firmware_name = "adsp.mdt",
    623		.pas_id = 1,
    624		.has_aggre2_clk = false,
    625		.auto_boot = true,
    626		.proxy_pd_names = (char*[]){
    627			"cx",
    628			NULL
    629		},
    630		.ssr_name = "lpass",
    631		.sysmon_name = "adsp",
    632		.ssctl_id = 0x14,
    633};
    634
    635static const struct adsp_data cdsp_resource_init = {
    636	.crash_reason_smem = 601,
    637	.firmware_name = "cdsp.mdt",
    638	.pas_id = 18,
    639	.has_aggre2_clk = false,
    640	.auto_boot = true,
    641	.ssr_name = "cdsp",
    642	.sysmon_name = "cdsp",
    643	.ssctl_id = 0x17,
    644};
    645
    646static const struct adsp_data sdm845_cdsp_resource_init = {
    647	.crash_reason_smem = 601,
    648	.firmware_name = "cdsp.mdt",
    649	.pas_id = 18,
    650	.has_aggre2_clk = false,
    651	.auto_boot = true,
    652	.load_state = "cdsp",
    653	.ssr_name = "cdsp",
    654	.sysmon_name = "cdsp",
    655	.ssctl_id = 0x17,
    656};
    657
    658static const struct adsp_data sm6350_cdsp_resource = {
    659	.crash_reason_smem = 601,
    660	.firmware_name = "cdsp.mdt",
    661	.pas_id = 18,
    662	.has_aggre2_clk = false,
    663	.auto_boot = true,
    664	.proxy_pd_names = (char*[]){
    665		"cx",
    666		"mx",
    667		NULL
    668	},
    669	.load_state = "cdsp",
    670	.ssr_name = "cdsp",
    671	.sysmon_name = "cdsp",
    672	.ssctl_id = 0x17,
    673};
    674
    675static const struct adsp_data sm8150_cdsp_resource = {
    676	.crash_reason_smem = 601,
    677	.firmware_name = "cdsp.mdt",
    678	.pas_id = 18,
    679	.has_aggre2_clk = false,
    680	.auto_boot = true,
    681	.proxy_pd_names = (char*[]){
    682		"cx",
    683		NULL
    684	},
    685	.load_state = "cdsp",
    686	.ssr_name = "cdsp",
    687	.sysmon_name = "cdsp",
    688	.ssctl_id = 0x17,
    689};
    690
    691static const struct adsp_data sm8250_cdsp_resource = {
    692	.crash_reason_smem = 601,
    693	.firmware_name = "cdsp.mdt",
    694	.pas_id = 18,
    695	.has_aggre2_clk = false,
    696	.auto_boot = true,
    697	.proxy_pd_names = (char*[]){
    698		"cx",
    699		NULL
    700	},
    701	.load_state = "cdsp",
    702	.ssr_name = "cdsp",
    703	.sysmon_name = "cdsp",
    704	.ssctl_id = 0x17,
    705};
    706
    707static const struct adsp_data sc8280xp_nsp0_resource = {
    708	.crash_reason_smem = 601,
    709	.firmware_name = "cdsp.mdt",
    710	.pas_id = 18,
    711	.has_aggre2_clk = false,
    712	.auto_boot = true,
    713	.proxy_pd_names = (char*[]){
    714		"nsp",
    715		NULL
    716	},
    717	.ssr_name = "cdsp0",
    718	.sysmon_name = "cdsp",
    719	.ssctl_id = 0x17,
    720};
    721
    722static const struct adsp_data sc8280xp_nsp1_resource = {
    723	.crash_reason_smem = 633,
    724	.firmware_name = "cdsp.mdt",
    725	.pas_id = 30,
    726	.has_aggre2_clk = false,
    727	.auto_boot = true,
    728	.proxy_pd_names = (char*[]){
    729		"nsp",
    730		NULL
    731	},
    732	.ssr_name = "cdsp1",
    733	.sysmon_name = "cdsp1",
    734	.ssctl_id = 0x20,
    735};
    736
    737static const struct adsp_data sm8350_cdsp_resource = {
    738	.crash_reason_smem = 601,
    739	.firmware_name = "cdsp.mdt",
    740	.pas_id = 18,
    741	.has_aggre2_clk = false,
    742	.auto_boot = true,
    743	.proxy_pd_names = (char*[]){
    744		"cx",
    745		"mxc",
    746		NULL
    747	},
    748	.load_state = "cdsp",
    749	.ssr_name = "cdsp",
    750	.sysmon_name = "cdsp",
    751	.ssctl_id = 0x17,
    752};
    753
    754static const struct adsp_data mpss_resource_init = {
    755	.crash_reason_smem = 421,
    756	.firmware_name = "modem.mdt",
    757	.pas_id = 4,
    758	.minidump_id = 3,
    759	.has_aggre2_clk = false,
    760	.auto_boot = false,
    761	.proxy_pd_names = (char*[]){
    762		"cx",
    763		"mss",
    764		NULL
    765	},
    766	.load_state = "modem",
    767	.ssr_name = "mpss",
    768	.sysmon_name = "modem",
    769	.ssctl_id = 0x12,
    770};
    771
    772static const struct adsp_data sc8180x_mpss_resource = {
    773	.crash_reason_smem = 421,
    774	.firmware_name = "modem.mdt",
    775	.pas_id = 4,
    776	.has_aggre2_clk = false,
    777	.auto_boot = false,
    778	.proxy_pd_names = (char*[]){
    779		"cx",
    780		NULL
    781	},
    782	.load_state = "modem",
    783	.ssr_name = "mpss",
    784	.sysmon_name = "modem",
    785	.ssctl_id = 0x12,
    786};
    787
    788static const struct adsp_data slpi_resource_init = {
    789		.crash_reason_smem = 424,
    790		.firmware_name = "slpi.mdt",
    791		.pas_id = 12,
    792		.has_aggre2_clk = true,
    793		.auto_boot = true,
    794		.proxy_pd_names = (char*[]){
    795			"ssc_cx",
    796			NULL
    797		},
    798		.ssr_name = "dsps",
    799		.sysmon_name = "slpi",
    800		.ssctl_id = 0x16,
    801};
    802
    803static const struct adsp_data sm8150_slpi_resource = {
    804		.crash_reason_smem = 424,
    805		.firmware_name = "slpi.mdt",
    806		.pas_id = 12,
    807		.has_aggre2_clk = false,
    808		.auto_boot = true,
    809		.proxy_pd_names = (char*[]){
    810			"lcx",
    811			"lmx",
    812			NULL
    813		},
    814		.load_state = "slpi",
    815		.ssr_name = "dsps",
    816		.sysmon_name = "slpi",
    817		.ssctl_id = 0x16,
    818};
    819
    820static const struct adsp_data sm8250_slpi_resource = {
    821	.crash_reason_smem = 424,
    822	.firmware_name = "slpi.mdt",
    823	.pas_id = 12,
    824	.has_aggre2_clk = false,
    825	.auto_boot = true,
    826	.proxy_pd_names = (char*[]){
    827		"lcx",
    828		"lmx",
    829		NULL
    830	},
    831	.load_state = "slpi",
    832	.ssr_name = "dsps",
    833	.sysmon_name = "slpi",
    834	.ssctl_id = 0x16,
    835};
    836
    837static const struct adsp_data sm8350_slpi_resource = {
    838	.crash_reason_smem = 424,
    839	.firmware_name = "slpi.mdt",
    840	.pas_id = 12,
    841	.has_aggre2_clk = false,
    842	.auto_boot = true,
    843	.proxy_pd_names = (char*[]){
    844		"lcx",
    845		"lmx",
    846		NULL
    847	},
    848	.load_state = "slpi",
    849	.ssr_name = "dsps",
    850	.sysmon_name = "slpi",
    851	.ssctl_id = 0x16,
    852};
    853
    854static const struct adsp_data wcss_resource_init = {
    855	.crash_reason_smem = 421,
    856	.firmware_name = "wcnss.mdt",
    857	.pas_id = 6,
    858	.auto_boot = true,
    859	.ssr_name = "mpss",
    860	.sysmon_name = "wcnss",
    861	.ssctl_id = 0x12,
    862};
    863
    864static const struct adsp_data sdx55_mpss_resource = {
    865	.crash_reason_smem = 421,
    866	.firmware_name = "modem.mdt",
    867	.pas_id = 4,
    868	.has_aggre2_clk = false,
    869	.auto_boot = true,
    870	.proxy_pd_names = (char*[]){
    871		"cx",
    872		"mss",
    873		NULL
    874	},
    875	.ssr_name = "mpss",
    876	.sysmon_name = "modem",
    877	.ssctl_id = 0x22,
    878};
    879
    880static const struct of_device_id adsp_of_match[] = {
    881	{ .compatible = "qcom,msm8226-adsp-pil", .data = &adsp_resource_init},
    882	{ .compatible = "qcom,msm8974-adsp-pil", .data = &adsp_resource_init},
    883	{ .compatible = "qcom,msm8996-adsp-pil", .data = &msm8996_adsp_resource},
    884	{ .compatible = "qcom,msm8996-slpi-pil", .data = &slpi_resource_init},
    885	{ .compatible = "qcom,msm8998-adsp-pas", .data = &msm8996_adsp_resource},
    886	{ .compatible = "qcom,msm8998-slpi-pas", .data = &slpi_resource_init},
    887	{ .compatible = "qcom,qcs404-adsp-pas", .data = &adsp_resource_init },
    888	{ .compatible = "qcom,qcs404-cdsp-pas", .data = &cdsp_resource_init },
    889	{ .compatible = "qcom,qcs404-wcss-pas", .data = &wcss_resource_init },
    890	{ .compatible = "qcom,sc7180-mpss-pas", .data = &mpss_resource_init},
    891	{ .compatible = "qcom,sc7280-mpss-pas", .data = &mpss_resource_init},
    892	{ .compatible = "qcom,sc8180x-adsp-pas", .data = &sm8150_adsp_resource},
    893	{ .compatible = "qcom,sc8180x-cdsp-pas", .data = &sm8150_cdsp_resource},
    894	{ .compatible = "qcom,sc8180x-mpss-pas", .data = &sc8180x_mpss_resource},
    895	{ .compatible = "qcom,sc8280xp-adsp-pas", .data = &sm8250_adsp_resource},
    896	{ .compatible = "qcom,sc8280xp-nsp0-pas", .data = &sc8280xp_nsp0_resource},
    897	{ .compatible = "qcom,sc8280xp-nsp1-pas", .data = &sc8280xp_nsp1_resource},
    898	{ .compatible = "qcom,sdm660-adsp-pas", .data = &adsp_resource_init},
    899	{ .compatible = "qcom,sdm845-adsp-pas", .data = &sdm845_adsp_resource_init},
    900	{ .compatible = "qcom,sdm845-cdsp-pas", .data = &sdm845_cdsp_resource_init},
    901	{ .compatible = "qcom,sdx55-mpss-pas", .data = &sdx55_mpss_resource},
    902	{ .compatible = "qcom,sm6350-adsp-pas", .data = &sm6350_adsp_resource},
    903	{ .compatible = "qcom,sm6350-cdsp-pas", .data = &sm6350_cdsp_resource},
    904	{ .compatible = "qcom,sm6350-mpss-pas", .data = &mpss_resource_init},
    905	{ .compatible = "qcom,sm8150-adsp-pas", .data = &sm8150_adsp_resource},
    906	{ .compatible = "qcom,sm8150-cdsp-pas", .data = &sm8150_cdsp_resource},
    907	{ .compatible = "qcom,sm8150-mpss-pas", .data = &mpss_resource_init},
    908	{ .compatible = "qcom,sm8150-slpi-pas", .data = &sm8150_slpi_resource},
    909	{ .compatible = "qcom,sm8250-adsp-pas", .data = &sm8250_adsp_resource},
    910	{ .compatible = "qcom,sm8250-cdsp-pas", .data = &sm8250_cdsp_resource},
    911	{ .compatible = "qcom,sm8250-slpi-pas", .data = &sm8250_slpi_resource},
    912	{ .compatible = "qcom,sm8350-adsp-pas", .data = &sm8350_adsp_resource},
    913	{ .compatible = "qcom,sm8350-cdsp-pas", .data = &sm8350_cdsp_resource},
    914	{ .compatible = "qcom,sm8350-slpi-pas", .data = &sm8350_slpi_resource},
    915	{ .compatible = "qcom,sm8350-mpss-pas", .data = &mpss_resource_init},
    916	{ .compatible = "qcom,sm8450-adsp-pas", .data = &sm8350_adsp_resource},
    917	{ .compatible = "qcom,sm8450-cdsp-pas", .data = &sm8350_cdsp_resource},
    918	{ .compatible = "qcom,sm8450-slpi-pas", .data = &sm8350_slpi_resource},
    919	{ .compatible = "qcom,sm8450-mpss-pas", .data = &mpss_resource_init},
    920	{ },
    921};
    922MODULE_DEVICE_TABLE(of, adsp_of_match);
    923
    924static struct platform_driver adsp_driver = {
    925	.probe = adsp_probe,
    926	.remove = adsp_remove,
    927	.driver = {
    928		.name = "qcom_q6v5_pas",
    929		.of_match_table = adsp_of_match,
    930	},
    931};
    932
    933module_platform_driver(adsp_driver);
    934MODULE_DESCRIPTION("Qualcomm Hexagon v5 Peripheral Authentication Service driver");
    935MODULE_LICENSE("GPL v2");