Commit 57e06f8c authored by Arnd Bergmann's avatar Arnd Bergmann

Merge tag 'qcom-drivers-for-6.7' of...

Merge tag 'qcom-drivers-for-6.7' of https://git.kernel.org/pub/scm/linux/kernel/git/qcom/linux into soc/drivers

Qualcomm driver updates for v6.7

This introduces partial support for the Qualcomm Secure Execution
Environment SCM interface, and uses this to implement EFI variable
access on the Windows On Snapdragon devices (for now).

The 32/64-bit calling convention detector of the SCM interface is
updated to not choose 64-bit convention when Linux is 32-bit. The
"extern" specifier is dropped from the interface include file.

The LLCC driver gains support for carrying configuration for multiple
different system/DDR configurations for a given platform, and selecting
between them. Support for Q[DR]U1000 is added to the driver.

All exported symbols are transitioned to EXPORT_SYMBOL_GPL().

The platform_drivers in the Qualcomm SoC are transitioned to the
void-returning remove_new implementation.

The rmtfs memory driver gains support for leaving guard pages around the
used area, to avoid issues if the allocation happens to be placed
adjacent to another protected memory region.

The socinfo driver gains knowledge about IPQ8174, QCM6490, SM7150P and
various PMICs used together with SM8550.

* tag 'qcom-drivers-for-6.7' of https://git.kernel.org/pub/scm/linux/kernel/git/qcom/linux: (44 commits)
  soc: qcom: socinfo: Convert to platform remove callback returning void
  soc: qcom: smsm: Convert to platform remove callback returning void
  soc: qcom: smp2p: Convert to platform remove callback returning void
  soc: qcom: smem: Convert to platform remove callback returning void
  soc: qcom: rmtfs_mem: Convert to platform remove callback returning void
  soc: qcom: qcom_stats: Convert to platform remove callback returning void
  soc: qcom: qcom_gsbi: Convert to platform remove callback returning void
  soc: qcom: qcom_aoss: Convert to platform remove callback returning void
  soc: qcom: pmic_glink: Convert to platform remove callback returning void
  soc: qcom: ocmem: Convert to platform remove callback returning void
  soc: qcom: llcc-qcom: Convert to platform remove callback returning void
  soc: qcom: icc-bwmon: Convert to platform remove callback returning void
  firmware: qcom_scm: use 64-bit calling convention only when client is 64-bit
  soc: qcom: llcc: Handle a second device without data corruption
  soc: qcom: Switch to EXPORT_SYMBOL_GPL()
  soc: qcom: smem: Annotate struct qcom_smem with __counted_by
  soc: qcom: rmtfs: Support discarding guard pages
  dt-bindings: reserved-memory: rmtfs: Allow guard pages
  dt-bindings: firmware: qcom,scm: document IPQ5018 compatible
  firmware: qcom_scm: disable SDI if required
  ...

Link: https://lore.kernel.org/r/20231015204014.855672-1-andersson@kernel.orgSigned-off-by: default avatarArnd Bergmann <arnd@arndb.de>
parents 09427e19 c0989f7d
......@@ -20,6 +20,7 @@ description: |
properties:
compatible:
enum:
- qcom,qdu1000-llcc
- qcom,sc7180-llcc
- qcom,sc7280-llcc
- qcom,sc8180x-llcc
......@@ -44,6 +45,14 @@ properties:
interrupts:
maxItems: 1
nvmem-cells:
items:
- description: Reference to an nvmem node for multi channel DDR
nvmem-cell-names:
items:
- const: multi-chan-ddr
required:
- compatible
- reg
......@@ -92,6 +101,7 @@ allOf:
compatible:
contains:
enum:
- qcom,qdu1000-llcc
- qcom,sc8180x-llcc
- qcom,sc8280xp-llcc
then:
......
......@@ -24,6 +24,7 @@ properties:
- qcom,scm-apq8064
- qcom,scm-apq8084
- qcom,scm-ipq4019
- qcom,scm-ipq5018
- qcom,scm-ipq5332
- qcom,scm-ipq6018
- qcom,scm-ipq806x
......@@ -56,6 +57,7 @@ properties:
- qcom,scm-sm6125
- qcom,scm-sm6350
- qcom,scm-sm6375
- qcom,scm-sm7150
- qcom,scm-sm8150
- qcom,scm-sm8250
- qcom,scm-sm8350
......@@ -89,6 +91,14 @@ properties:
protocol to handle sleeping SCM calls.
maxItems: 1
qcom,sdi-enabled:
description:
Indicates that the SDI (Secure Debug Image) has been enabled by TZ
by default and it needs to be disabled.
If not disabled WDT assertion or reboot will cause the board to hang
in the debug mode.
type: boolean
qcom,dload-mode:
$ref: /schemas/types.yaml#/definitions/phandle-array
items:
......
......@@ -26,6 +26,17 @@ properties:
description: >
identifier of the client to use this region for buffers
qcom,use-guard-pages:
type: boolean
description: >
Indicates that the firmware, or hardware, does not gracefully handle
memory protection of this region when placed adjacent to other protected
memory regions, and that padding around the used portion of the memory
region is necessary.
When this is set, the first and last page should be left unused, and the
effective size of the region will thereby shrink with two pages.
qcom,vmid:
$ref: /schemas/types.yaml#/definitions/uint32-array
description: >
......
......@@ -52,6 +52,8 @@ properties:
iommus:
maxItems: 1
dma-coherent: true
required:
- compatible
- reg
......
......@@ -17801,6 +17801,18 @@ S: Maintained
F: Documentation/devicetree/bindings/mtd/qcom,nandc.yaml
F: drivers/mtd/nand/raw/qcom_nandc.c
QUALCOMM QSEECOM DRIVER
M: Maximilian Luz <luzmaximilian@gmail.com>
L: linux-arm-msm@vger.kernel.org
S: Maintained
F: drivers/firmware/qcom_qseecom.c
QUALCOMM QSEECOM UEFISECAPP DRIVER
M: Maximilian Luz <luzmaximilian@gmail.com>
L: linux-arm-msm@vger.kernel.org
S: Maintained
F: drivers/firmware/qcom_qseecom_uefisecapp.c
QUALCOMM RMNET DRIVER
M: Subash Abhinov Kasiviswanathan <quic_subashab@quicinc.com>
M: Sean Tranchetti <quic_stranche@quicinc.com>
......
......@@ -226,6 +226,39 @@ config QCOM_SCM_DOWNLOAD_MODE_DEFAULT
Say Y here to enable "download mode" by default.
config QCOM_QSEECOM
bool "Qualcomm QSEECOM interface driver"
depends on QCOM_SCM=y
select AUXILIARY_BUS
help
Various Qualcomm SoCs have a Secure Execution Environment (SEE) running
in the Trust Zone. This module provides an interface to that via the
QSEECOM mechanism, using SCM calls.
The QSEECOM interface allows, among other things, access to applications
running in the SEE. An example of such an application is 'uefisecapp',
which is required to access UEFI variables on certain systems. If
selected, the interface will also attempt to detect and register client
devices for supported applications.
Select Y here to enable the QSEECOM interface driver.
config QCOM_QSEECOM_UEFISECAPP
bool "Qualcomm SEE UEFI Secure App client driver"
depends on QCOM_QSEECOM
depends on EFI
help
Various Qualcomm SoCs do not allow direct access to EFI variables.
Instead, these need to be accessed via the UEFI Secure Application
(uefisecapp), residing in the Secure Execution Environment (SEE).
This module provides a client driver for uefisecapp, installing efivar
operations to allow the kernel accessing EFI variables, and via that also
provide user-space with access to EFI variables via efivarfs.
Select Y here to provide access to EFI variables on the aforementioned
platforms.
config SYSFB
bool
select BOOT_VESA_SUPPORT
......
......@@ -20,6 +20,8 @@ obj-$(CONFIG_RASPBERRYPI_FIRMWARE) += raspberrypi.o
obj-$(CONFIG_FW_CFG_SYSFS) += qemu_fw_cfg.o
obj-$(CONFIG_QCOM_SCM) += qcom-scm.o
qcom-scm-objs += qcom_scm.o qcom_scm-smc.o qcom_scm-legacy.o
obj-$(CONFIG_QCOM_QSEECOM) += qcom_qseecom.o
obj-$(CONFIG_QCOM_QSEECOM_UEFISECAPP) += qcom_qseecom_uefisecapp.o
obj-$(CONFIG_SYSFB) += sysfb.o
obj-$(CONFIG_SYSFB_SIMPLEFB) += sysfb_simplefb.o
obj-$(CONFIG_TI_SCI_PROTOCOL) += ti_sci.o
......
// SPDX-License-Identifier: GPL-2.0-or-later
/*
* Driver for Qualcomm Secure Execution Environment (SEE) interface (QSEECOM).
* Responsible for setting up and managing QSEECOM client devices.
*
* Copyright (C) 2023 Maximilian Luz <luzmaximilian@gmail.com>
*/
#include <linux/auxiliary_bus.h>
#include <linux/module.h>
#include <linux/platform_device.h>
#include <linux/slab.h>
#include <linux/types.h>
#include <linux/firmware/qcom/qcom_qseecom.h>
#include <linux/firmware/qcom/qcom_scm.h>
struct qseecom_app_desc {
const char *app_name;
const char *dev_name;
};
static void qseecom_client_release(struct device *dev)
{
struct qseecom_client *client;
client = container_of(dev, struct qseecom_client, aux_dev.dev);
kfree(client);
}
static void qseecom_client_remove(void *data)
{
struct qseecom_client *client = data;
auxiliary_device_delete(&client->aux_dev);
auxiliary_device_uninit(&client->aux_dev);
}
static int qseecom_client_register(struct platform_device *qseecom_dev,
const struct qseecom_app_desc *desc)
{
struct qseecom_client *client;
u32 app_id;
int ret;
/* Try to find the app ID, skip device if not found */
ret = qcom_scm_qseecom_app_get_id(desc->app_name, &app_id);
if (ret)
return ret == -ENOENT ? 0 : ret;
dev_info(&qseecom_dev->dev, "setting up client for %s\n", desc->app_name);
/* Allocate and set-up the client device */
client = kzalloc(sizeof(*client), GFP_KERNEL);
if (!client)
return -ENOMEM;
client->aux_dev.name = desc->dev_name;
client->aux_dev.dev.parent = &qseecom_dev->dev;
client->aux_dev.dev.release = qseecom_client_release;
client->app_id = app_id;
ret = auxiliary_device_init(&client->aux_dev);
if (ret) {
kfree(client);
return ret;
}
ret = auxiliary_device_add(&client->aux_dev);
if (ret) {
auxiliary_device_uninit(&client->aux_dev);
return ret;
}
ret = devm_add_action_or_reset(&qseecom_dev->dev, qseecom_client_remove, client);
if (ret)
return ret;
return 0;
}
/*
* List of supported applications. One client device will be created per entry,
* assuming the app has already been loaded (usually by firmware bootloaders)
* and its ID can be queried successfully.
*/
static const struct qseecom_app_desc qcom_qseecom_apps[] = {
{ "qcom.tz.uefisecapp", "uefisecapp" },
};
static int qcom_qseecom_probe(struct platform_device *qseecom_dev)
{
int ret;
int i;
/* Set up client devices for each base application */
for (i = 0; i < ARRAY_SIZE(qcom_qseecom_apps); i++) {
ret = qseecom_client_register(qseecom_dev, &qcom_qseecom_apps[i]);
if (ret)
return ret;
}
return 0;
}
static struct platform_driver qcom_qseecom_driver = {
.driver = {
.name = "qcom_qseecom",
},
.probe = qcom_qseecom_probe,
};
static int __init qcom_qseecom_init(void)
{
return platform_driver_register(&qcom_qseecom_driver);
}
subsys_initcall(qcom_qseecom_init);
MODULE_AUTHOR("Maximilian Luz <luzmaximilian@gmail.com>");
MODULE_DESCRIPTION("Driver for the Qualcomm SEE (QSEECOM) interface");
MODULE_LICENSE("GPL");
This diff is collapsed.
This diff is collapsed.
......@@ -80,6 +80,7 @@ extern int scm_legacy_call(struct device *dev, const struct qcom_scm_desc *desc,
#define QCOM_SCM_SVC_BOOT 0x01
#define QCOM_SCM_BOOT_SET_ADDR 0x01
#define QCOM_SCM_BOOT_TERMINATE_PC 0x02
#define QCOM_SCM_BOOT_SDI_CONFIG 0x09
#define QCOM_SCM_BOOT_SET_DLOAD_MODE 0x10
#define QCOM_SCM_BOOT_SET_ADDR_MC 0x11
#define QCOM_SCM_BOOT_SET_REMOTE_STATE 0x0a
......
......@@ -133,7 +133,7 @@ int cmd_db_ready(void)
return 0;
}
EXPORT_SYMBOL(cmd_db_ready);
EXPORT_SYMBOL_GPL(cmd_db_ready);
static int cmd_db_get_header(const char *id, const struct entry_header **eh,
const struct rsc_hdr **rh)
......@@ -193,7 +193,7 @@ u32 cmd_db_read_addr(const char *id)
return ret < 0 ? 0 : le32_to_cpu(ent->addr);
}
EXPORT_SYMBOL(cmd_db_read_addr);
EXPORT_SYMBOL_GPL(cmd_db_read_addr);
/**
* cmd_db_read_aux_data() - Query command db for aux data.
......@@ -218,7 +218,7 @@ const void *cmd_db_read_aux_data(const char *id, size_t *len)
return rsc_offset(rsc_hdr, ent);
}
EXPORT_SYMBOL(cmd_db_read_aux_data);
EXPORT_SYMBOL_GPL(cmd_db_read_aux_data);
/**
* cmd_db_read_slave_id - Get the slave ID for a given resource address
......@@ -240,7 +240,7 @@ enum cmd_db_hw_type cmd_db_read_slave_id(const char *id)
addr = le32_to_cpu(ent->addr);
return (addr >> SLAVE_ID_SHIFT) & SLAVE_ID_MASK;
}
EXPORT_SYMBOL(cmd_db_read_slave_id);
EXPORT_SYMBOL_GPL(cmd_db_read_slave_id);
#ifdef CONFIG_DEBUG_FS
static int cmd_db_debugfs_dump(struct seq_file *seq, void *p)
......
......@@ -793,13 +793,11 @@ static int bwmon_probe(struct platform_device *pdev)
return 0;
}
static int bwmon_remove(struct platform_device *pdev)
static void bwmon_remove(struct platform_device *pdev)
{
struct icc_bwmon *bwmon = platform_get_drvdata(pdev);
bwmon_disable(bwmon);
return 0;
}
static const struct icc_bwmon_data msm8998_bwmon_data = {
......@@ -862,7 +860,7 @@ MODULE_DEVICE_TABLE(of, bwmon_of_match);
static struct platform_driver bwmon_driver = {
.probe = bwmon_probe,
.remove = bwmon_remove,
.remove_new = bwmon_remove,
.driver = {
.name = "qcom-bwmon",
.of_match_table = bwmon_of_match,
......
......@@ -32,7 +32,7 @@ void kryo_l2_set_indirect_reg(u64 reg, u64 val)
isb();
raw_spin_unlock_irqrestore(&l2_access_lock, flags);
}
EXPORT_SYMBOL(kryo_l2_set_indirect_reg);
EXPORT_SYMBOL_GPL(kryo_l2_set_indirect_reg);
/**
* kryo_l2_get_indirect_reg() - read an L2 register value
......@@ -54,4 +54,4 @@ u64 kryo_l2_get_indirect_reg(u64 reg)
return val;
}
EXPORT_SYMBOL(kryo_l2_get_indirect_reg);
EXPORT_SYMBOL_GPL(kryo_l2_get_indirect_reg);
This diff is collapsed.
......@@ -211,7 +211,7 @@ struct ocmem *of_get_ocmem(struct device *dev)
}
return ocmem;
}
EXPORT_SYMBOL(of_get_ocmem);
EXPORT_SYMBOL_GPL(of_get_ocmem);
struct ocmem_buf *ocmem_allocate(struct ocmem *ocmem, enum ocmem_client client,
unsigned long size)
......@@ -267,7 +267,7 @@ struct ocmem_buf *ocmem_allocate(struct ocmem *ocmem, enum ocmem_client client,
return ERR_PTR(ret);
}
EXPORT_SYMBOL(ocmem_allocate);
EXPORT_SYMBOL_GPL(ocmem_allocate);
void ocmem_free(struct ocmem *ocmem, enum ocmem_client client,
struct ocmem_buf *buf)
......@@ -294,7 +294,7 @@ void ocmem_free(struct ocmem *ocmem, enum ocmem_client client,
clear_bit_unlock(BIT(client), &ocmem->active_allocations);
}
EXPORT_SYMBOL(ocmem_free);
EXPORT_SYMBOL_GPL(ocmem_free);
static int ocmem_dev_probe(struct platform_device *pdev)
{
......@@ -416,14 +416,12 @@ static int ocmem_dev_probe(struct platform_device *pdev)
return ret;
}
static int ocmem_dev_remove(struct platform_device *pdev)
static void ocmem_dev_remove(struct platform_device *pdev)
{
struct ocmem *ocmem = platform_get_drvdata(pdev);
clk_disable_unprepare(ocmem->core_clk);
clk_disable_unprepare(ocmem->iface_clk);
return 0;
}
static const struct ocmem_config ocmem_8226_config = {
......@@ -446,7 +444,7 @@ MODULE_DEVICE_TABLE(of, ocmem_of_match);
static struct platform_driver ocmem_driver = {
.probe = ocmem_dev_probe,
.remove = ocmem_dev_remove,
.remove_new = ocmem_dev_remove,
.driver = {
.name = "ocmem",
.of_match_table = ocmem_of_match,
......
......@@ -554,7 +554,7 @@ struct pdr_service *pdr_add_lookup(struct pdr_handle *pdr,
kfree(pds);
return ERR_PTR(ret);
}
EXPORT_SYMBOL(pdr_add_lookup);
EXPORT_SYMBOL_GPL(pdr_add_lookup);
/**
* pdr_restart_pd() - restart PD
......@@ -634,7 +634,7 @@ int pdr_restart_pd(struct pdr_handle *pdr, struct pdr_service *pds)
return 0;
}
EXPORT_SYMBOL(pdr_restart_pd);
EXPORT_SYMBOL_GPL(pdr_restart_pd);
/**
* pdr_handle_alloc() - initialize the PDR client handle
......@@ -715,7 +715,7 @@ struct pdr_handle *pdr_handle_alloc(void (*status)(int state,
return ERR_PTR(ret);
}
EXPORT_SYMBOL(pdr_handle_alloc);
EXPORT_SYMBOL_GPL(pdr_handle_alloc);
/**
* pdr_handle_release() - release the PDR client handle
......@@ -749,7 +749,7 @@ void pdr_handle_release(struct pdr_handle *pdr)
kfree(pdr);
}
EXPORT_SYMBOL(pdr_handle_release);
EXPORT_SYMBOL_GPL(pdr_handle_release);
MODULE_LICENSE("GPL v2");
MODULE_DESCRIPTION("Qualcomm Protection Domain Restart helpers");
......@@ -318,7 +318,7 @@ static int pmic_glink_probe(struct platform_device *pdev)
return ret;
}
static int pmic_glink_remove(struct platform_device *pdev)
static void pmic_glink_remove(struct platform_device *pdev)
{
struct pmic_glink *pg = dev_get_drvdata(&pdev->dev);
......@@ -334,8 +334,6 @@ static int pmic_glink_remove(struct platform_device *pdev)
mutex_lock(&__pmic_glink_lock);
__pmic_glink = NULL;
mutex_unlock(&__pmic_glink_lock);
return 0;
}
static const unsigned long pmic_glink_sm8450_client_mask = BIT(PMIC_GLINK_CLIENT_BATT) |
......@@ -352,7 +350,7 @@ MODULE_DEVICE_TABLE(of, pmic_glink_of_match);
static struct platform_driver pmic_glink_driver = {
.probe = pmic_glink_probe,
.remove = pmic_glink_remove,
.remove_new = pmic_glink_remove,
.driver = {
.name = "qcom_pmic_glink",
.of_match_table = pmic_glink_of_match,
......
......@@ -444,6 +444,7 @@ static int pmic_glink_altmode_probe(struct auxiliary_device *adev,
ret = fwnode_property_read_u32(fwnode, "reg", &port);
if (ret < 0) {
dev_err(dev, "missing reg property of %pOFn\n", fwnode);
fwnode_handle_put(fwnode);
return ret;
}
......@@ -454,6 +455,7 @@ static int pmic_glink_altmode_probe(struct auxiliary_device *adev,
if (altmode->ports[port].altmode) {
dev_err(dev, "multiple connector definition for port %u\n", port);
fwnode_handle_put(fwnode);
return -EINVAL;
}
......@@ -468,45 +470,59 @@ static int pmic_glink_altmode_probe(struct auxiliary_device *adev,
alt_port->bridge.type = DRM_MODE_CONNECTOR_USB;
ret = devm_drm_bridge_add(dev, &alt_port->bridge);
if (ret)
if (ret) {
fwnode_handle_put(fwnode);
return ret;
}
alt_port->dp_alt.svid = USB_TYPEC_DP_SID;
alt_port->dp_alt.mode = USB_TYPEC_DP_MODE;
alt_port->dp_alt.active = 1;
alt_port->typec_mux = fwnode_typec_mux_get(fwnode);
if (IS_ERR(alt_port->typec_mux))
if (IS_ERR(alt_port->typec_mux)) {
fwnode_handle_put(fwnode);
return dev_err_probe(dev, PTR_ERR(alt_port->typec_mux),
"failed to acquire mode-switch for port: %d\n",
port);
}
ret = devm_add_action_or_reset(dev, pmic_glink_altmode_put_mux,
alt_port->typec_mux);
if (ret)
if (ret) {
fwnode_handle_put(fwnode);
return ret;
}
alt_port->typec_retimer = fwnode_typec_retimer_get(fwnode);
if (IS_ERR(alt_port->typec_retimer))
if (IS_ERR(alt_port->typec_retimer)) {
fwnode_handle_put(fwnode);
return dev_err_probe(dev, PTR_ERR(alt_port->typec_retimer),
"failed to acquire retimer-switch for port: %d\n",
port);
}
ret = devm_add_action_or_reset(dev, pmic_glink_altmode_put_retimer,
alt_port->typec_retimer);
if (ret)
if (ret) {
fwnode_handle_put(fwnode);
return ret;
}
alt_port->typec_switch = fwnode_typec_switch_get(fwnode);
if (IS_ERR(alt_port->typec_switch))
if (IS_ERR(alt_port->typec_switch)) {
fwnode_handle_put(fwnode);
return dev_err_probe(dev, PTR_ERR(alt_port->typec_switch),
"failed to acquire orientation-switch for port: %d\n",
port);
}
ret = devm_add_action_or_reset(dev, pmic_glink_altmode_put_switch,
alt_port->typec_switch);
if (ret)
if (ret) {
fwnode_handle_put(fwnode);
return ret;
}
}
altmode->client = devm_pmic_glink_register_client(dev,
......
......@@ -199,7 +199,7 @@ u32 geni_se_get_qup_hw_version(struct geni_se *se)
return readl_relaxed(wrapper->base + QUP_HW_VER_REG);
}
EXPORT_SYMBOL(geni_se_get_qup_hw_version);
EXPORT_SYMBOL_GPL(geni_se_get_qup_hw_version);
static void geni_se_io_set_mode(void __iomem *base)
{
......@@ -272,7 +272,7 @@ void geni_se_init(struct geni_se *se, u32 rx_wm, u32 rx_rfr)
val |= S_COMMON_GENI_S_IRQ_EN;
writel_relaxed(val, se->base + SE_GENI_S_IRQ_EN);
}
EXPORT_SYMBOL(geni_se_init);
EXPORT_SYMBOL_GPL(geni_se_init);
static void geni_se_select_fifo_mode(struct geni_se *se)
{
......@@ -364,7 +364,7 @@ void geni_se_select_mode(struct geni_se *se, enum geni_se_xfer_mode mode)
break;
}
}
EXPORT_SYMBOL(geni_se_select_mode);
EXPORT_SYMBOL_GPL(geni_se_select_mode);
/**
* DOC: Overview
......@@ -481,7 +481,7 @@ void geni_se_config_packing(struct geni_se *se, int bpw, int pack_words,
if (pack_words || bpw == 32)
writel_relaxed(bpw / 16, se->base + SE_GENI_BYTE_GRAN);
}
EXPORT_SYMBOL(geni_se_config_packing);
EXPORT_SYMBOL_GPL(geni_se_config_packing);
static void geni_se_clks_off(struct geni_se *se)
{
......@@ -512,7 +512,7 @@ int geni_se_resources_off(struct geni_se *se)
geni_se_clks_off(se);
return 0;
}
EXPORT_SYMBOL(geni_se_resources_off);
EXPORT_SYMBOL_GPL(geni_se_resources_off);
static int geni_se_clks_on(struct geni_se *se)
{
......@@ -553,7 +553,7 @@ int geni_se_resources_on(struct geni_se *se)
return ret;
}
EXPORT_SYMBOL(geni_se_resources_on);
EXPORT_SYMBOL_GPL(geni_se_resources_on);
/**
* geni_se_clk_tbl_get() - Get the clock table to program DFS
......@@ -594,7 +594,7 @@ int geni_se_clk_tbl_get(struct geni_se *se, unsigned long **tbl)
*tbl = se->clk_perf_tbl;
return se->num_clk_levels;
}
EXPORT_SYMBOL(geni_se_clk_tbl_get);
EXPORT_SYMBOL_GPL(geni_se_clk_tbl_get);
/**
* geni_se_clk_freq_match() - Get the matching or closest SE clock frequency
......@@ -656,7 +656,7 @@ int geni_se_clk_freq_match(struct geni_se *se, unsigned long req_freq,
return 0;
}
EXPORT_SYMBOL(geni_se_clk_freq_match);
EXPORT_SYMBOL_GPL(geni_se_clk_freq_match);
#define GENI_SE_DMA_DONE_EN BIT(0)
#define GENI_SE_DMA_EOT_EN BIT(1)
......@@ -684,7 +684,7 @@ void geni_se_tx_init_dma(struct geni_se *se, dma_addr_t iova, size_t len)
writel_relaxed(GENI_SE_DMA_EOT_BUF, se->base + SE_DMA_TX_ATTR);
writel(len, se->base + SE_DMA_TX_LEN);
}
EXPORT_SYMBOL(geni_se_tx_init_dma);
EXPORT_SYMBOL_GPL(geni_se_tx_init_dma);
/**
* geni_se_tx_dma_prep() - Prepare the serial engine for TX DMA transfer
......@@ -712,7 +712,7 @@ int geni_se_tx_dma_prep(struct geni_se *se, void *buf, size_t len,
geni_se_tx_init_dma(se, *iova, len);
return 0;
}
EXPORT_SYMBOL(geni_se_tx_dma_prep);
EXPORT_SYMBOL_GPL(geni_se_tx_dma_prep);
/**
* geni_se_rx_init_dma() - Initiate RX DMA transfer on the serial engine
......@@ -736,7 +736,7 @@ void geni_se_rx_init_dma(struct geni_se *se, dma_addr_t iova, size_t len)
writel_relaxed(0, se->base + SE_DMA_RX_ATTR);
writel(len, se->base + SE_DMA_RX_LEN);
}
EXPORT_SYMBOL(geni_se_rx_init_dma);
EXPORT_SYMBOL_GPL(geni_se_rx_init_dma);
/**
* geni_se_rx_dma_prep() - Prepare the serial engine for RX DMA transfer
......@@ -764,7 +764,7 @@ int geni_se_rx_dma_prep(struct geni_se *se, void *buf, size_t len,
geni_se_rx_init_dma(se, *iova, len);
return 0;
}
EXPORT_SYMBOL(geni_se_rx_dma_prep);
EXPORT_SYMBOL_GPL(geni_se_rx_dma_prep);
/**
* geni_se_tx_dma_unprep() - Unprepare the serial engine after TX DMA transfer
......@@ -781,7 +781,7 @@ void geni_se_tx_dma_unprep(struct geni_se *se, dma_addr_t iova, size_t len)
if (!dma_mapping_error(wrapper->dev, iova))
dma_unmap_single(wrapper->dev, iova, len, DMA_TO_DEVICE);
}
EXPORT_SYMBOL(geni_se_tx_dma_unprep);
EXPORT_SYMBOL_GPL(geni_se_tx_dma_unprep);
/**
* geni_se_rx_dma_unprep() - Unprepare the serial engine after RX DMA transfer
......@@ -798,7 +798,7 @@ void geni_se_rx_dma_unprep(struct geni_se *se, dma_addr_t iova, size_t len)
if (!dma_mapping_error(wrapper->dev, iova))
dma_unmap_single(wrapper->dev, iova, len, DMA_FROM_DEVICE);
}
EXPORT_SYMBOL(geni_se_rx_dma_unprep);
EXPORT_SYMBOL_GPL(geni_se_rx_dma_unprep);
int geni_icc_get(struct geni_se *se, const char *icc_ddr)
{
......@@ -827,7 +827,7 @@ int geni_icc_get(struct geni_se *se, const char *icc_ddr)
return err;
}
EXPORT_SYMBOL(geni_icc_get);
EXPORT_SYMBOL_GPL(geni_icc_get);
int geni_icc_set_bw(struct geni_se *se)
{
......@@ -845,7 +845,7 @@ int geni_icc_set_bw(struct geni_se *se)
return 0;
}
EXPORT_SYMBOL(geni_icc_set_bw);
EXPORT_SYMBOL_GPL(geni_icc_set_bw);
void geni_icc_set_tag(struct geni_se *se, u32 tag)
{
......@@ -854,7 +854,7 @@ void geni_icc_set_tag(struct geni_se *se, u32 tag)
for (i = 0; i < ARRAY_SIZE(se->icc_paths); i++)
icc_set_tag(se->icc_paths[i].path, tag);
}
EXPORT_SYMBOL(geni_icc_set_tag);
EXPORT_SYMBOL_GPL(geni_icc_set_tag);
/* To do: Replace this by icc_bulk_enable once it's implemented in ICC core */
int geni_icc_enable(struct geni_se *se)
......@@ -872,7 +872,7 @@ int geni_icc_enable(struct geni_se *se)
return 0;
}
EXPORT_SYMBOL(geni_icc_enable);
EXPORT_SYMBOL_GPL(geni_icc_enable);
int geni_icc_disable(struct geni_se *se)
{
......@@ -889,7 +889,7 @@ int geni_icc_disable(struct geni_se *se)
return 0;
}
EXPORT_SYMBOL(geni_icc_disable);
EXPORT_SYMBOL_GPL(geni_icc_disable);
static int geni_se_probe(struct platform_device *pdev)
{
......
......@@ -260,7 +260,7 @@ int qmp_send(struct qmp *qmp, const char *fmt, ...)
return ret;
}
EXPORT_SYMBOL(qmp_send);
EXPORT_SYMBOL_GPL(qmp_send);
static int qmp_qdss_clk_prepare(struct clk_hw *hw)
{
......@@ -458,7 +458,7 @@ struct qmp *qmp_get(struct device *dev)
}
return qmp;
}
EXPORT_SYMBOL(qmp_get);
EXPORT_SYMBOL_GPL(qmp_get);
/**
* qmp_put() - release a qmp handle
......@@ -473,7 +473,7 @@ void qmp_put(struct qmp *qmp)
if (!IS_ERR_OR_NULL(qmp))
put_device(qmp->dev);
}
EXPORT_SYMBOL(qmp_put);
EXPORT_SYMBOL_GPL(qmp_put);
static int qmp_probe(struct platform_device *pdev)
{
......@@ -533,7 +533,7 @@ static int qmp_probe(struct platform_device *pdev)
return ret;
}
static int qmp_remove(struct platform_device *pdev)
static void qmp_remove(struct platform_device *pdev)
{
struct qmp *qmp = platform_get_drvdata(pdev);
......@@ -542,8 +542,6 @@ static int qmp_remove(struct platform_device *pdev)
qmp_close(qmp);
mbox_free_channel(qmp->mbox_chan);
return 0;
}
static const struct of_device_id qmp_dt_match[] = {
......@@ -565,7 +563,7 @@ static struct platform_driver qmp_driver = {
.suppress_bind_attrs = true,
},
.probe = qmp_probe,
.remove = qmp_remove,
.remove_new = qmp_remove,
};
module_platform_driver(qmp_driver);
......
......@@ -212,13 +212,11 @@ static int gsbi_probe(struct platform_device *pdev)
return of_platform_populate(node, NULL, NULL, &pdev->dev);
}
static int gsbi_remove(struct platform_device *pdev)
static void gsbi_remove(struct platform_device *pdev)
{
struct gsbi_info *gsbi = platform_get_drvdata(pdev);
clk_disable_unprepare(gsbi->hclk);
return 0;
}
static const struct of_device_id gsbi_dt_match[] = {
......@@ -234,7 +232,7 @@ static struct platform_driver gsbi_driver = {
.of_match_table = gsbi_dt_match,
},
.probe = gsbi_probe,
.remove = gsbi_remove,
.remove_new = gsbi_remove,
};
module_platform_driver(gsbi_driver);
......
......@@ -216,13 +216,11 @@ static int qcom_stats_probe(struct platform_device *pdev)
return 0;
}
static int qcom_stats_remove(struct platform_device *pdev)
static void qcom_stats_remove(struct platform_device *pdev)
{
struct dentry *root = platform_get_drvdata(pdev);
debugfs_remove_recursive(root);
return 0;
}
static const struct stats_config rpm_data = {
......@@ -272,7 +270,7 @@ MODULE_DEVICE_TABLE(of, qcom_stats_table);
static struct platform_driver qcom_stats = {
.probe = qcom_stats_probe,
.remove = qcom_stats_remove,
.remove_new = qcom_stats_remove,
.driver = {
.name = "qcom_stats",
.of_match_table = qcom_stats_table,
......
......@@ -754,7 +754,7 @@ void *qmi_encode_message(int type, unsigned int msg_id, size_t *len,
return msg;
}
EXPORT_SYMBOL(qmi_encode_message);
EXPORT_SYMBOL_GPL(qmi_encode_message);
/**
* qmi_decode_message() - Decode QMI encoded message to C structure
......@@ -778,7 +778,7 @@ int qmi_decode_message(const void *buf, size_t len,
return qmi_decode(ei, c_struct, buf + sizeof(struct qmi_header),
len - sizeof(struct qmi_header), 1);
}
EXPORT_SYMBOL(qmi_decode_message);
EXPORT_SYMBOL_GPL(qmi_decode_message);
/* Common header in all QMI responses */
const struct qmi_elem_info qmi_response_type_v01_ei[] = {
......@@ -810,7 +810,7 @@ const struct qmi_elem_info qmi_response_type_v01_ei[] = {
.ei_array = NULL,
},
};
EXPORT_SYMBOL(qmi_response_type_v01_ei);
EXPORT_SYMBOL_GPL(qmi_response_type_v01_ei);
MODULE_DESCRIPTION("QMI encoder/decoder helper");
MODULE_LICENSE("GPL v2");
......@@ -223,7 +223,7 @@ int qmi_add_lookup(struct qmi_handle *qmi, unsigned int service,
return 0;
}
EXPORT_SYMBOL(qmi_add_lookup);
EXPORT_SYMBOL_GPL(qmi_add_lookup);
static void qmi_send_new_server(struct qmi_handle *qmi, struct qmi_service *svc)
{
......@@ -287,7 +287,7 @@ int qmi_add_server(struct qmi_handle *qmi, unsigned int service,
return 0;
}
EXPORT_SYMBOL(qmi_add_server);
EXPORT_SYMBOL_GPL(qmi_add_server);
/**
* qmi_txn_init() - allocate transaction id within the given QMI handle
......@@ -328,7 +328,7 @@ int qmi_txn_init(struct qmi_handle *qmi, struct qmi_txn *txn,
return ret;
}
EXPORT_SYMBOL(qmi_txn_init);
EXPORT_SYMBOL_GPL(qmi_txn_init);
/**
* qmi_txn_wait() - wait for a response on a transaction
......@@ -359,7 +359,7 @@ int qmi_txn_wait(struct qmi_txn *txn, unsigned long timeout)
else
return txn->result;
}
EXPORT_SYMBOL(qmi_txn_wait);
EXPORT_SYMBOL_GPL(qmi_txn_wait);
/**
* qmi_txn_cancel() - cancel an ongoing transaction
......@@ -375,7 +375,7 @@ void qmi_txn_cancel(struct qmi_txn *txn)
mutex_unlock(&txn->lock);
mutex_unlock(&qmi->txn_lock);
}
EXPORT_SYMBOL(qmi_txn_cancel);
EXPORT_SYMBOL_GPL(qmi_txn_cancel);
/**
* qmi_invoke_handler() - find and invoke a handler for a message
......@@ -676,7 +676,7 @@ int qmi_handle_init(struct qmi_handle *qmi, size_t recv_buf_size,
return ret;
}
EXPORT_SYMBOL(qmi_handle_init);
EXPORT_SYMBOL_GPL(qmi_handle_init);
/**
* qmi_handle_release() - release the QMI client handle
......@@ -717,7 +717,7 @@ void qmi_handle_release(struct qmi_handle *qmi)
kfree(svc);
}
}
EXPORT_SYMBOL(qmi_handle_release);
EXPORT_SYMBOL_GPL(qmi_handle_release);
/**
* qmi_send_message() - send a QMI message
......@@ -796,7 +796,7 @@ ssize_t qmi_send_request(struct qmi_handle *qmi, struct sockaddr_qrtr *sq,
return qmi_send_message(qmi, sq, txn, QMI_REQUEST, msg_id, len, ei,
c_struct);
}
EXPORT_SYMBOL(qmi_send_request);
EXPORT_SYMBOL_GPL(qmi_send_request);
/**
* qmi_send_response() - send a response QMI message
......@@ -817,7 +817,7 @@ ssize_t qmi_send_response(struct qmi_handle *qmi, struct sockaddr_qrtr *sq,
return qmi_send_message(qmi, sq, txn, QMI_RESPONSE, msg_id, len, ei,
c_struct);
}
EXPORT_SYMBOL(qmi_send_response);
EXPORT_SYMBOL_GPL(qmi_send_response);
/**
* qmi_send_indication() - send an indication QMI message
......@@ -851,4 +851,4 @@ ssize_t qmi_send_indication(struct qmi_handle *qmi, struct sockaddr_qrtr *sq,
return rval;
}
EXPORT_SYMBOL(qmi_send_indication);
EXPORT_SYMBOL_GPL(qmi_send_indication);
......@@ -200,6 +200,15 @@ static int qcom_rmtfs_mem_probe(struct platform_device *pdev)
rmtfs_mem->client_id = client_id;
rmtfs_mem->size = rmem->size;
/*
* If requested, discard the first and last 4k block in order to ensure
* that the rmtfs region isn't adjacent to other protected regions.
*/
if (of_property_read_bool(node, "qcom,use-guard-pages")) {
rmtfs_mem->addr += SZ_4K;
rmtfs_mem->size -= 2 * SZ_4K;
}
device_initialize(&rmtfs_mem->dev);
rmtfs_mem->dev.parent = &pdev->dev;
rmtfs_mem->dev.groups = qcom_rmtfs_mem_groups;
......@@ -281,7 +290,7 @@ static int qcom_rmtfs_mem_probe(struct platform_device *pdev)
return ret;
}
static int qcom_rmtfs_mem_remove(struct platform_device *pdev)
static void qcom_rmtfs_mem_remove(struct platform_device *pdev)
{
struct qcom_rmtfs_mem *rmtfs_mem = dev_get_drvdata(&pdev->dev);
struct qcom_scm_vmperm perm;
......@@ -296,8 +305,6 @@ static int qcom_rmtfs_mem_remove(struct platform_device *pdev)
cdev_device_del(&rmtfs_mem->cdev, &rmtfs_mem->dev);
put_device(&rmtfs_mem->dev);
return 0;
}
static const struct of_device_id qcom_rmtfs_mem_of_match[] = {
......@@ -308,7 +315,7 @@ MODULE_DEVICE_TABLE(of, qcom_rmtfs_mem_of_match);
static struct platform_driver qcom_rmtfs_mem_driver = {
.probe = qcom_rmtfs_mem_probe,
.remove = qcom_rmtfs_mem_remove,
.remove_new = qcom_rmtfs_mem_remove,
.driver = {
.name = "qcom_rmtfs_mem",
.of_match_table = qcom_rmtfs_mem_of_match,
......
......@@ -239,7 +239,7 @@ int rpmh_write_async(const struct device *dev, enum rpmh_state state,
return __rpmh_write(dev, state, rpm_msg);
}
EXPORT_SYMBOL(rpmh_write_async);
EXPORT_SYMBOL_GPL(rpmh_write_async);
/**
* rpmh_write: Write a set of RPMH commands and block until response
......@@ -270,7 +270,7 @@ int rpmh_write(const struct device *dev, enum rpmh_state state,
WARN_ON(!ret);
return (ret > 0) ? 0 : -ETIMEDOUT;
}
EXPORT_SYMBOL(rpmh_write);
EXPORT_SYMBOL_GPL(rpmh_write);
static void cache_batch(struct rpmh_ctrlr *ctrlr, struct batch_cache_req *req)
{
......@@ -395,7 +395,7 @@ int rpmh_write_batch(const struct device *dev, enum rpmh_state state,
return ret;
}
EXPORT_SYMBOL(rpmh_write_batch);
EXPORT_SYMBOL_GPL(rpmh_write_batch);
static int is_req_valid(struct cache_req *req)
{
......@@ -500,4 +500,4 @@ void rpmh_invalidate(const struct device *dev)
ctrlr->dirty = true;
spin_unlock_irqrestore(&ctrlr->cache_lock, flags);
}
EXPORT_SYMBOL(rpmh_invalidate);
EXPORT_SYMBOL_GPL(rpmh_invalidate);
......@@ -142,7 +142,7 @@ int qcom_rpm_smd_write(struct qcom_smd_rpm *rpm,
mutex_unlock(&rpm->lock);
return ret;
}
EXPORT_SYMBOL(qcom_rpm_smd_write);
EXPORT_SYMBOL_GPL(qcom_rpm_smd_write);
static int qcom_smd_rpm_callback(struct rpmsg_device *rpdev,
void *data,
......
......@@ -285,7 +285,7 @@ struct qcom_smem {
struct smem_partition partitions[SMEM_HOST_COUNT];
unsigned num_regions;
struct smem_region regions[];
struct smem_region regions[] __counted_by(num_regions);
};
static void *
......@@ -368,7 +368,7 @@ bool qcom_smem_is_available(void)
{
return !!__smem;
}
EXPORT_SYMBOL(qcom_smem_is_available);
EXPORT_SYMBOL_GPL(qcom_smem_is_available);
static int qcom_smem_alloc_private(struct qcom_smem *smem,
struct smem_partition *part,
......@@ -1187,14 +1187,12 @@ static int qcom_smem_probe(struct platform_device *pdev)
return 0;
}
static int qcom_smem_remove(struct platform_device *pdev)
static void qcom_smem_remove(struct platform_device *pdev)
{
platform_device_unregister(__smem->socinfo);
hwspin_lock_free(__smem->hwlock);
__smem = NULL;
return 0;
}
static const struct of_device_id qcom_smem_of_match[] = {
......@@ -1205,7 +1203,7 @@ MODULE_DEVICE_TABLE(of, qcom_smem_of_match);
static struct platform_driver qcom_smem_driver = {
.probe = qcom_smem_probe,
.remove = qcom_smem_remove,
.remove_new = qcom_smem_remove,
.driver = {
.name = "qcom-smem",
.of_match_table = qcom_smem_of_match,
......
......@@ -660,7 +660,7 @@ static int qcom_smp2p_probe(struct platform_device *pdev)
return -EINVAL;
}
static int qcom_smp2p_remove(struct platform_device *pdev)
static void qcom_smp2p_remove(struct platform_device *pdev)
{
struct qcom_smp2p *smp2p = platform_get_drvdata(pdev);
struct smp2p_entry *entry;
......@@ -676,8 +676,6 @@ static int qcom_smp2p_remove(struct platform_device *pdev)
mbox_free_channel(smp2p->mbox_chan);
smp2p->out->valid_entries = 0;
return 0;
}
static const struct of_device_id qcom_smp2p_of_match[] = {
......@@ -688,7 +686,7 @@ MODULE_DEVICE_TABLE(of, qcom_smp2p_of_match);
static struct platform_driver qcom_smp2p_driver = {
.probe = qcom_smp2p_probe,
.remove = qcom_smp2p_remove,
.remove_new = qcom_smp2p_remove,
.driver = {
.name = "qcom_smp2p",
.of_match_table = qcom_smp2p_of_match,
......
......@@ -613,7 +613,7 @@ static int qcom_smsm_probe(struct platform_device *pdev)
return ret;
}
static int qcom_smsm_remove(struct platform_device *pdev)
static void qcom_smsm_remove(struct platform_device *pdev)
{
struct qcom_smsm *smsm = platform_get_drvdata(pdev);
unsigned id;
......@@ -623,8 +623,6 @@ static int qcom_smsm_remove(struct platform_device *pdev)
irq_domain_remove(smsm->entries[id].domain);
qcom_smem_state_unregister(smsm->state);
return 0;
}
static const struct of_device_id qcom_smsm_of_match[] = {
......@@ -635,7 +633,7 @@ MODULE_DEVICE_TABLE(of, qcom_smsm_of_match);
static struct platform_driver qcom_smsm_driver = {
.probe = qcom_smsm_probe,
.remove = qcom_smsm_remove,
.remove_new = qcom_smsm_remove,
.driver = {
.name = "qcom-smsm",
.of_match_table = qcom_smsm_of_match,
......
......@@ -117,6 +117,12 @@ static const char *const pmic_models[] = {
[55] = "PM2250",
[58] = "PM8450",
[65] = "PM8010",
[69] = "PM8550VS",
[70] = "PM8550VE",
[71] = "PM8550B",
[72] = "PMR735D",
[73] = "PM8550",
[74] = "PMK8550",
};
struct socinfo_params {
......@@ -349,6 +355,7 @@ static const struct soc_id soc_id[] = {
{ qcom_board_id(SDA439) },
{ qcom_board_id(SDA429) },
{ qcom_board_id(SM7150) },
{ qcom_board_id(SM7150P) },
{ qcom_board_id(IPQ8070) },
{ qcom_board_id(IPQ8071) },
{ qcom_board_id(QM215) },
......@@ -359,6 +366,9 @@ static const struct soc_id soc_id[] = {
{ qcom_board_id(SM6125) },
{ qcom_board_id(IPQ8070A) },
{ qcom_board_id(IPQ8071A) },
{ qcom_board_id(IPQ8172) },
{ qcom_board_id(IPQ8173) },
{ qcom_board_id(IPQ8174) },
{ qcom_board_id(IPQ6018) },
{ qcom_board_id(IPQ6028) },
{ qcom_board_id(SDM429W) },
......@@ -389,6 +399,7 @@ static const struct soc_id soc_id[] = {
{ qcom_board_id_named(SM8450_3, "SM8450") },
{ qcom_board_id(SC7280) },
{ qcom_board_id(SC7180P) },
{ qcom_board_id(QCM6490) },
{ qcom_board_id(IPQ5000) },
{ qcom_board_id(IPQ0509) },
{ qcom_board_id(IPQ0518) },
......@@ -776,20 +787,18 @@ static int qcom_socinfo_probe(struct platform_device *pdev)
return 0;
}
static int qcom_socinfo_remove(struct platform_device *pdev)
static void qcom_socinfo_remove(struct platform_device *pdev)
{
struct qcom_socinfo *qs = platform_get_drvdata(pdev);
soc_device_unregister(qs->soc_dev);
socinfo_debugfs_exit(qs);
return 0;
}
static struct platform_driver qcom_socinfo_driver = {
.probe = qcom_socinfo_probe,
.remove = qcom_socinfo_remove,
.remove_new = qcom_socinfo_remove,
.driver = {
.name = "qcom-socinfo",
},
......
......@@ -287,7 +287,7 @@ struct rpmsg_endpoint *qcom_wcnss_open_channel(void *wcnss, const char *name, rp
return rpmsg_create_ept(_wcnss->channel->rpdev, cb, priv, chinfo);
}
EXPORT_SYMBOL(qcom_wcnss_open_channel);
EXPORT_SYMBOL_GPL(qcom_wcnss_open_channel);
static void wcnss_async_probe(struct work_struct *work)
{
......@@ -355,7 +355,6 @@ static struct rpmsg_driver wcnss_ctrl_driver = {
.callback = wcnss_ctrl_smd_callback,
.drv = {
.name = "qcom_wcnss_ctrl",
.owner = THIS_MODULE,
.of_match_table = wcnss_ctrl_of_match,
},
};
......
......@@ -193,6 +193,7 @@
#define QCOM_ID_SDA439 363
#define QCOM_ID_SDA429 364
#define QCOM_ID_SM7150 365
#define QCOM_ID_SM7150P 366
#define QCOM_ID_IPQ8070 375
#define QCOM_ID_IPQ8071 376
#define QCOM_ID_QM215 386
......@@ -203,6 +204,9 @@
#define QCOM_ID_SM6125 394
#define QCOM_ID_IPQ8070A 395
#define QCOM_ID_IPQ8071A 396
#define QCOM_ID_IPQ8172 397
#define QCOM_ID_IPQ8173 398
#define QCOM_ID_IPQ8174 399
#define QCOM_ID_IPQ6018 402
#define QCOM_ID_IPQ6028 403
#define QCOM_ID_SDM429W 416
......@@ -233,6 +237,7 @@
#define QCOM_ID_SM8450_3 482
#define QCOM_ID_SC7280 487
#define QCOM_ID_SC7180P 495
#define QCOM_ID_QCM6490 497
#define QCOM_ID_IPQ5000 503
#define QCOM_ID_IPQ0509 504
#define QCOM_ID_IPQ0518 505
......
/* SPDX-License-Identifier: GPL-2.0-or-later */
/*
* Driver for Qualcomm Secure Execution Environment (SEE) interface (QSEECOM).
* Responsible for setting up and managing QSEECOM client devices.
*
* Copyright (C) 2023 Maximilian Luz <luzmaximilian@gmail.com>
*/
#include <linux/auxiliary_bus.h>
#include <linux/types.h>
#include <linux/firmware/qcom/qcom_scm.h>
/**
* struct qseecom_client - QSEECOM client device.
* @aux_dev: Underlying auxiliary device.
* @app_id: ID of the loaded application.
*/
struct qseecom_client {
struct auxiliary_device aux_dev;
u32 app_id;
};
/**
* qcom_qseecom_app_send() - Send to and receive data from a given QSEE app.
* @client: The QSEECOM client associated with the target app.
* @req: Request buffer sent to the app (must be DMA-mappable).
* @req_size: Size of the request buffer.
* @rsp: Response buffer, written to by the app (must be DMA-mappable).
* @rsp_size: Size of the response buffer.
*
* Sends a request to the QSEE app associated with the given client and read
* back its response. The caller must provide two DMA memory regions, one for
* the request and one for the response, and fill out the @req region with the
* respective (app-specific) request data. The QSEE app reads this and returns
* its response in the @rsp region.
*
* Note: This is a convenience wrapper around qcom_scm_qseecom_app_send().
* Clients should prefer to use this wrapper.
*
* Return: Zero on success, nonzero on failure.
*/
static inline int qcom_qseecom_app_send(struct qseecom_client *client, void *req, size_t req_size,
void *rsp, size_t rsp_size)
{
return qcom_scm_qseecom_app_send(client->app_id, req, req_size, rsp, rsp_size);
}
......@@ -59,12 +59,12 @@ enum qcom_scm_ice_cipher {
#define QCOM_SCM_PERM_RW (QCOM_SCM_PERM_READ | QCOM_SCM_PERM_WRITE)
#define QCOM_SCM_PERM_RWX (QCOM_SCM_PERM_RW | QCOM_SCM_PERM_EXEC)
extern bool qcom_scm_is_available(void);
bool qcom_scm_is_available(void);
extern int qcom_scm_set_cold_boot_addr(void *entry);
extern int qcom_scm_set_warm_boot_addr(void *entry);
extern void qcom_scm_cpu_power_down(u32 flags);
extern int qcom_scm_set_remote_state(u32 state, u32 id);
int qcom_scm_set_cold_boot_addr(void *entry);
int qcom_scm_set_warm_boot_addr(void *entry);
void qcom_scm_cpu_power_down(u32 flags);
int qcom_scm_set_remote_state(u32 state, u32 id);
struct qcom_scm_pas_metadata {
void *ptr;
......@@ -72,54 +72,69 @@ struct qcom_scm_pas_metadata {
ssize_t size;
};
extern int qcom_scm_pas_init_image(u32 peripheral, const void *metadata,
size_t size,
struct qcom_scm_pas_metadata *ctx);
extern void qcom_scm_pas_metadata_release(struct qcom_scm_pas_metadata *ctx);
extern int qcom_scm_pas_mem_setup(u32 peripheral, phys_addr_t addr,
phys_addr_t size);
extern int qcom_scm_pas_auth_and_reset(u32 peripheral);
extern int qcom_scm_pas_shutdown(u32 peripheral);
extern bool qcom_scm_pas_supported(u32 peripheral);
extern int qcom_scm_io_readl(phys_addr_t addr, unsigned int *val);
extern int qcom_scm_io_writel(phys_addr_t addr, unsigned int val);
extern bool qcom_scm_restore_sec_cfg_available(void);
extern int qcom_scm_restore_sec_cfg(u32 device_id, u32 spare);
extern int qcom_scm_iommu_secure_ptbl_size(u32 spare, size_t *size);
extern int qcom_scm_iommu_secure_ptbl_init(u64 addr, u32 size, u32 spare);
extern int qcom_scm_iommu_set_cp_pool_size(u32 spare, u32 size);
extern int qcom_scm_mem_protect_video_var(u32 cp_start, u32 cp_size,
u32 cp_nonpixel_start,
u32 cp_nonpixel_size);
extern int qcom_scm_assign_mem(phys_addr_t mem_addr, size_t mem_sz,
u64 *src,
const struct qcom_scm_vmperm *newvm,
unsigned int dest_cnt);
extern bool qcom_scm_ocmem_lock_available(void);
extern int qcom_scm_ocmem_lock(enum qcom_scm_ocmem_client id, u32 offset,
u32 size, u32 mode);
extern int qcom_scm_ocmem_unlock(enum qcom_scm_ocmem_client id, u32 offset,
u32 size);
extern bool qcom_scm_ice_available(void);
extern int qcom_scm_ice_invalidate_key(u32 index);
extern int qcom_scm_ice_set_key(u32 index, const u8 *key, u32 key_size,
enum qcom_scm_ice_cipher cipher,
u32 data_unit_size);
extern bool qcom_scm_hdcp_available(void);
extern int qcom_scm_hdcp_req(struct qcom_scm_hdcp_req *req, u32 req_cnt,
u32 *resp);
extern int qcom_scm_iommu_set_pt_format(u32 sec_id, u32 ctx_num, u32 pt_fmt);
extern int qcom_scm_qsmmu500_wait_safe_toggle(bool en);
extern int qcom_scm_lmh_dcvsh(u32 payload_fn, u32 payload_reg, u32 payload_val,
u64 limit_node, u32 node_id, u64 version);
extern int qcom_scm_lmh_profile_change(u32 profile_id);
extern bool qcom_scm_lmh_dcvsh_available(void);
int qcom_scm_pas_init_image(u32 peripheral, const void *metadata, size_t size,
struct qcom_scm_pas_metadata *ctx);
void qcom_scm_pas_metadata_release(struct qcom_scm_pas_metadata *ctx);
int qcom_scm_pas_mem_setup(u32 peripheral, phys_addr_t addr, phys_addr_t size);
int qcom_scm_pas_auth_and_reset(u32 peripheral);
int qcom_scm_pas_shutdown(u32 peripheral);
bool qcom_scm_pas_supported(u32 peripheral);
int qcom_scm_io_readl(phys_addr_t addr, unsigned int *val);
int qcom_scm_io_writel(phys_addr_t addr, unsigned int val);
bool qcom_scm_restore_sec_cfg_available(void);
int qcom_scm_restore_sec_cfg(u32 device_id, u32 spare);
int qcom_scm_iommu_secure_ptbl_size(u32 spare, size_t *size);
int qcom_scm_iommu_secure_ptbl_init(u64 addr, u32 size, u32 spare);
int qcom_scm_iommu_set_cp_pool_size(u32 spare, u32 size);
int qcom_scm_mem_protect_video_var(u32 cp_start, u32 cp_size,
u32 cp_nonpixel_start, u32 cp_nonpixel_size);
int qcom_scm_assign_mem(phys_addr_t mem_addr, size_t mem_sz, u64 *src,
const struct qcom_scm_vmperm *newvm,
unsigned int dest_cnt);
bool qcom_scm_ocmem_lock_available(void);
int qcom_scm_ocmem_lock(enum qcom_scm_ocmem_client id, u32 offset, u32 size,
u32 mode);
int qcom_scm_ocmem_unlock(enum qcom_scm_ocmem_client id, u32 offset, u32 size);
bool qcom_scm_ice_available(void);
int qcom_scm_ice_invalidate_key(u32 index);
int qcom_scm_ice_set_key(u32 index, const u8 *key, u32 key_size,
enum qcom_scm_ice_cipher cipher, u32 data_unit_size);
bool qcom_scm_hdcp_available(void);
int qcom_scm_hdcp_req(struct qcom_scm_hdcp_req *req, u32 req_cnt, u32 *resp);
int qcom_scm_iommu_set_pt_format(u32 sec_id, u32 ctx_num, u32 pt_fmt);
int qcom_scm_qsmmu500_wait_safe_toggle(bool en);
int qcom_scm_lmh_dcvsh(u32 payload_fn, u32 payload_reg, u32 payload_val,
u64 limit_node, u32 node_id, u64 version);
int qcom_scm_lmh_profile_change(u32 profile_id);
bool qcom_scm_lmh_dcvsh_available(void);
#ifdef CONFIG_QCOM_QSEECOM
int qcom_scm_qseecom_app_get_id(const char *app_name, u32 *app_id);
int qcom_scm_qseecom_app_send(u32 app_id, void *req, size_t req_size, void *rsp,
size_t rsp_size);
#else /* CONFIG_QCOM_QSEECOM */
static inline int qcom_scm_qseecom_app_get_id(const char *app_name, u32 *app_id)
{
return -EINVAL;
}
static inline int qcom_scm_qseecom_app_send(u32 app_id, void *req,
size_t req_size, void *rsp,
size_t rsp_size)
{
return -EINVAL;
}
#endif /* CONFIG_QCOM_QSEECOM */
#endif
......@@ -127,6 +127,12 @@ static inline int nvmem_cell_write(struct nvmem_cell *cell,
return -EOPNOTSUPP;
}
static inline int nvmem_cell_read_u8(struct device *dev,
const char *cell_id, u8 *val)
{
return -EOPNOTSUPP;
}
static inline int nvmem_cell_read_u16(struct device *dev,
const char *cell_id, u16 *val)
{
......
......@@ -30,7 +30,7 @@
#define LLCC_NPU 23
#define LLCC_WLHW 24
#define LLCC_PIMEM 25
#define LLCC_DRE 26
#define LLCC_ECC 26
#define LLCC_CVP 28
#define LLCC_MODPE 29
#define LLCC_APTCM 30
......
......@@ -10,6 +10,7 @@ typedef u16 ucs2_char_t;
unsigned long ucs2_strnlen(const ucs2_char_t *s, size_t maxlength);
unsigned long ucs2_strlen(const ucs2_char_t *s);
unsigned long ucs2_strsize(const ucs2_char_t *data, unsigned long maxlength);
ssize_t ucs2_strscpy(ucs2_char_t *dst, const ucs2_char_t *src, size_t count);
int ucs2_strncmp(const ucs2_char_t *a, const ucs2_char_t *b, size_t len);
unsigned long ucs2_utf8size(const ucs2_char_t *src);
......
......@@ -32,6 +32,58 @@ ucs2_strsize(const ucs2_char_t *data, unsigned long maxlength)
}
EXPORT_SYMBOL(ucs2_strsize);
/**
* ucs2_strscpy() - Copy a UCS2 string into a sized buffer.
*
* @dst: Pointer to the destination buffer where to copy the string to.
* @src: Pointer to the source buffer where to copy the string from.
* @count: Size of the destination buffer, in UCS2 (16-bit) characters.
*
* Like strscpy(), only for UCS2 strings.
*
* Copy the source string @src, or as much of it as fits, into the destination
* buffer @dst. The behavior is undefined if the string buffers overlap. The
* destination buffer @dst is always NUL-terminated, unless it's zero-sized.
*
* Return: The number of characters copied into @dst (excluding the trailing
* %NUL terminator) or -E2BIG if @count is 0 or @src was truncated due to the
* destination buffer being too small.
*/
ssize_t ucs2_strscpy(ucs2_char_t *dst, const ucs2_char_t *src, size_t count)
{
long res;
/*
* Ensure that we have a valid amount of space. We need to store at
* least one NUL-character.
*/
if (count == 0 || WARN_ON_ONCE(count > INT_MAX / sizeof(*dst)))
return -E2BIG;
/*
* Copy at most 'count' characters, return early if we find a
* NUL-terminator.
*/
for (res = 0; res < count; res++) {
ucs2_char_t c;
c = src[res];
dst[res] = c;
if (!c)
return res;
}
/*
* The loop above terminated without finding a NUL-terminator,
* exceeding the 'count': Enforce proper NUL-termination and return
* error.
*/
dst[count - 1] = 0;
return -E2BIG;
}
EXPORT_SYMBOL(ucs2_strscpy);
int
ucs2_strncmp(const ucs2_char_t *a, const ucs2_char_t *b, size_t len)
{
......
Markdown is supported
0%
or
You are about to add 0 people to the discussion. Proceed with caution.
Finish editing this message first!
Please register or to comment