// SPDX-License-Identifier: GPL-2.0-or-later /* * Copyright (C) 2006-2010 Freescale Semiconductor, Inc. All rights reserved. * * Authors: Shlomi Gridish <[email protected]> * Li Yang <[email protected]> * Based on cpm2_common.c from Dan Malek ([email protected]) * * Description: * General Purpose functions for the global management of the * QUICC Engine (QE). */ #include <linux/bitmap.h> #include <linux/errno.h> #include <linux/sched.h> #include <linux/kernel.h> #include <linux/param.h> #include <linux/string.h> #include <linux/spinlock.h> #include <linux/mm.h> #include <linux/interrupt.h> #include <linux/module.h> #include <linux/delay.h> #include <linux/ioport.h> #include <linux/iopoll.h> #include <linux/crc32.h> #include <linux/mod_devicetable.h> #include <linux/of.h> #include <linux/platform_device.h> #include <soc/fsl/qe/immap_qe.h> #include <soc/fsl/qe/qe.h> static void qe_snums_init(void); static int qe_sdma_init(void); static DEFINE_SPINLOCK(qe_lock); DEFINE_SPINLOCK(…); EXPORT_SYMBOL(…); /* We allocate this here because it is used almost exclusively for * the communication processor devices. */ struct qe_immap __iomem *qe_immr; EXPORT_SYMBOL(…); static u8 snums[QE_NUM_OF_SNUM]; /* Dynamically allocated SNUMs */ static DECLARE_BITMAP(snum_state, QE_NUM_OF_SNUM); static unsigned int qe_num_of_snum; static phys_addr_t qebase = …; static struct device_node *qe_get_device_node(void) { … } static phys_addr_t get_qe_base(void) { … } void qe_reset(void) { … } int qe_issue_cmd(u32 cmd, u32 device, u8 mcn_protocol, u32 cmd_input) { … } EXPORT_SYMBOL(…); /* Set a baud rate generator. This needs lots of work. There are * 16 BRGs, which can be connected to the QE channels or output * as clocks. The BRGs are in two different block of internal * memory mapped space. * The BRG clock is the QE clock divided by 2. * It was set up long ago during the initial boot phase and is * given to us. * Baud rate clocks are zero-based in the driver code (as that maps * to port numbers). Documentation uses 1-based numbering. */ static unsigned int brg_clk = …; #define CLK_GRAN … #define CLK_GRAN_LIMIT … unsigned int qe_get_brg_clk(void) { … } EXPORT_SYMBOL(…); #define PVR_VER_836x … #define PVR_VER_832x … static bool qe_general4_errata(void) { … } /* Program the BRG to the given sampling rate and multiplier * * @brg: the BRG, QE_BRG1 - QE_BRG16 * @rate: the desired sampling rate * @multiplier: corresponds to the value programmed in GUMR_L[RDCR] or * GUMR_L[TDCR]. E.g., if this BRG is the RX clock, and GUMR_L[RDCR]=01, * then 'multiplier' should be 8. */ int qe_setbrg(enum qe_clock brg, unsigned int rate, unsigned int multiplier) { … } EXPORT_SYMBOL(…); /* Convert a string to a QE clock source enum * * This function takes a string, typically from a property in the device * tree, and returns the corresponding "enum qe_clock" value. */ enum qe_clock qe_clock_source(const char *source) { … } EXPORT_SYMBOL(…); /* Initialize SNUMs (thread serial numbers) according to * QE Module Control chapter, SNUM table */ static void qe_snums_init(void) { … } int qe_get_snum(void) { … } EXPORT_SYMBOL(…); void qe_put_snum(u8 snum) { … } EXPORT_SYMBOL(…); static int qe_sdma_init(void) { … } /* The maximum number of RISCs we support */ #define MAX_QE_RISC … /* Firmware information stored here for qe_get_firmware_info() */ static struct qe_firmware_info qe_firmware_info; /* * Set to 1 if QE firmware has been uploaded, and therefore * qe_firmware_info contains valid data. */ static int qe_firmware_uploaded; /* * Upload a QE microcode * * This function is a worker function for qe_upload_firmware(). It does * the actual uploading of the microcode. */ static void qe_upload_microcode(const void *base, const struct qe_microcode *ucode) { … } /* * Upload a microcode to the I-RAM at a specific address. * * See Documentation/arch/powerpc/qe_firmware.rst for information on QE microcode * uploading. * * Currently, only version 1 is supported, so the 'version' field must be * set to 1. * * The SOC model and revision are not validated, they are only displayed for * informational purposes. * * 'calc_size' is the calculated size, in bytes, of the firmware structure and * all of the microcode structures, minus the CRC. * * 'length' is the size that the structure says it is, including the CRC. */ int qe_upload_firmware(const struct qe_firmware *firmware) { … } EXPORT_SYMBOL(…); /* * Get info on the currently-loaded firmware * * This function also checks the device tree to see if the boot loader has * uploaded a firmware already. */ struct qe_firmware_info *qe_get_firmware_info(void) { … } EXPORT_SYMBOL(…); unsigned int qe_get_num_of_risc(void) { … } EXPORT_SYMBOL(…); unsigned int qe_get_num_of_snums(void) { … } EXPORT_SYMBOL(…); static int __init qe_init(void) { … } subsys_initcall(qe_init); #if defined(CONFIG_SUSPEND) && defined(CONFIG_PPC_85xx) static int qe_resume(struct platform_device *ofdev) { if (!qe_alive_during_sleep()) qe_reset(); return 0; } static int qe_probe(struct platform_device *ofdev) { return 0; } static const struct of_device_id qe_ids[] = { { .compatible = "fsl,qe", }, { }, }; static struct platform_driver qe_driver = { .driver = { .name = "fsl-qe", .of_match_table = qe_ids, }, .probe = qe_probe, .resume = qe_resume, }; builtin_platform_driver(qe_driver); #endif /* defined(CONFIG_SUSPEND) && defined(CONFIG_PPC_85xx) */