// SPDX-License-Identifier: GPL-2.0+ /* * CAAM control-plane driver backend * Controller-level driver, kernel property detection, initialization * * Copyright 2008-2012 Freescale Semiconductor, Inc. * Copyright 2018-2019, 2023 NXP */ #include <linux/device.h> #include <linux/of_address.h> #include <linux/of_irq.h> #include <linux/platform_device.h> #include <linux/sys_soc.h> #include <linux/fsl/mc.h> #include "compat.h" #include "debugfs.h" #include "regs.h" #include "intern.h" #include "jr.h" #include "desc_constr.h" #include "ctrl.h" bool caam_dpaa2; EXPORT_SYMBOL(…); #ifdef CONFIG_CAAM_QI #include "qi.h" #endif /* * Descriptor to instantiate RNG State Handle 0 in normal mode and * load the JDKEK, TDKEK and TDSK registers */ static void build_instantiation_desc(u32 *desc, int handle, int do_sk) { … } /* Descriptor for deinstantiation of State Handle 0 of the RNG block. */ static void build_deinstantiation_desc(u32 *desc, int handle) { … } #ifdef CONFIG_OF static const struct of_device_id imx8m_machine_match[] = …; #endif /* * run_descriptor_deco0 - runs a descriptor on DECO0, under direct control of * the software (no JR/QI used). * @ctrldev - pointer to device * @status - descriptor status, after being run * * Return: - 0 if no error occurred * - -ENODEV if the DECO couldn't be acquired * - -EAGAIN if an error occurred while executing the descriptor */ static inline int run_descriptor_deco0(struct device *ctrldev, u32 *desc, u32 *status) { … } /* * deinstantiate_rng - builds and executes a descriptor on DECO0, * which deinitializes the RNG block. * @ctrldev - pointer to device * @state_handle_mask - bitmask containing the instantiation status * for the RNG4 state handles which exist in * the RNG4 block: 1 if it's been instantiated * * Return: - 0 if no error occurred * - -ENOMEM if there isn't enough memory to allocate the descriptor * - -ENODEV if DECO0 couldn't be acquired * - -EAGAIN if an error occurred when executing the descriptor */ static int deinstantiate_rng(struct device *ctrldev, int state_handle_mask) { … } static void devm_deinstantiate_rng(void *data) { … } /* * instantiate_rng - builds and executes a descriptor on DECO0, * which initializes the RNG block. * @ctrldev - pointer to device * @state_handle_mask - bitmask containing the instantiation status * for the RNG4 state handles which exist in * the RNG4 block: 1 if it's been instantiated * by an external entry, 0 otherwise. * @gen_sk - generate data to be loaded into the JDKEK, TDKEK and TDSK; * Caution: this can be done only once; if the keys need to be * regenerated, a POR is required * * Return: - 0 if no error occurred * - -ENOMEM if there isn't enough memory to allocate the descriptor * - -ENODEV if DECO0 couldn't be acquired * - -EAGAIN if an error occurred when executing the descriptor * f.i. there was a RNG hardware error due to not "good enough" * entropy being acquired. */ static int instantiate_rng(struct device *ctrldev, int state_handle_mask, int gen_sk) { … } /* * kick_trng - sets the various parameters for enabling the initialization * of the RNG4 block in CAAM * @dev - pointer to the controller device * @ent_delay - Defines the length (in system clocks) of each entropy sample. */ static void kick_trng(struct device *dev, int ent_delay) { … } static int caam_get_era_from_hw(struct caam_perfmon __iomem *perfmon) { … } /** * caam_get_era() - Return the ERA of the SEC on SoC, based * on "sec-era" optional property in the DTS. This property is updated * by u-boot. * In case this property is not passed an attempt to retrieve the CAAM * era via register reads will be made. * * @perfmon: Performance Monitor Registers */ static int caam_get_era(struct caam_perfmon __iomem *perfmon) { … } /* * ERRATA: imx6 devices (imx6D, imx6Q, imx6DL, imx6S, imx6DP and imx6QP) * have an issue wherein AXI bus transactions may not occur in the correct * order. This isn't a problem running single descriptors, but can be if * running multiple concurrent descriptors. Reworking the driver to throttle * to single requests is impractical, thus the workaround is to limit the AXI * pipeline to a depth of 1 (from it's default of 4) to preclude this situation * from occurring. */ static void handle_imx6_err005766(u32 __iomem *mcr) { … } static const struct of_device_id caam_match[] = …; MODULE_DEVICE_TABLE(of, caam_match); struct caam_imx_data { … }; static const struct clk_bulk_data caam_imx6_clks[] = …; static const struct caam_imx_data caam_imx6_data = …; static const struct clk_bulk_data caam_imx7_clks[] = …; static const struct caam_imx_data caam_imx7_data = …; static const struct clk_bulk_data caam_imx6ul_clks[] = …; static const struct caam_imx_data caam_imx6ul_data = …; static const struct clk_bulk_data caam_vf610_clks[] = …; static const struct caam_imx_data caam_vf610_data = …; static const struct caam_imx_data caam_imx8ulp_data; static const struct soc_device_attribute caam_imx_soc_table[] = …; static void disable_clocks(void *data) { … } static int init_clocks(struct device *dev, const struct caam_imx_data *data) { … } static void caam_remove_debugfs(void *root) { … } #ifdef CONFIG_FSL_MC_BUS static bool check_version(struct fsl_mc_version *mc_version, u32 major, u32 minor, u32 revision) { … } #endif static bool needs_entropy_delay_adjustment(void) { … } static int caam_ctrl_rng_init(struct device *dev) { … } /* Indicate if the internal state of the CAAM is lost during PM */ static int caam_off_during_pm(void) { … } static void caam_state_save(struct device *dev) { … } static void caam_state_restore(const struct device *dev) { … } static int caam_ctrl_suspend(struct device *dev) { … } static int caam_ctrl_resume(struct device *dev) { … } static DEFINE_SIMPLE_DEV_PM_OPS(caam_ctrl_pm_ops, caam_ctrl_suspend, caam_ctrl_resume); /* Probe routine for CAAM top (controller) level */ static int caam_probe(struct platform_device *pdev) { … } static struct platform_driver caam_driver = …; module_platform_driver(…) …; MODULE_LICENSE(…) …; MODULE_DESCRIPTION(…) …; MODULE_AUTHOR(…) …;