1 /* 2 * Copyright (c) 2019-2022 Arm Limited 3 * 4 * Licensed under the Apache License, Version 2.0 (the "License"); 5 * you may not use this file except in compliance with the License. 6 * You may obtain a copy of the License at 7 * 8 * http://www.apache.org/licenses/LICENSE-2.0 9 * 10 * Unless required by applicable law or agreed to in writing, software 11 * distributed under the License is distributed on an "AS IS" BASIS, 12 * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. 13 * See the License for the specific language governing permissions and 14 * limitations under the License. 15 */ 16 17 /** 18 * \file ppc_rss_drv.h 19 * \brief Generic driver for RSS Peripheral Protection Controllers (PPC). 20 */ 21 22 #ifndef __PPC_RSS_DRV_H__ 23 #define __PPC_RSS_DRV_H__ 24 25 #include <stdint.h> 26 #include <stdbool.h> 27 28 #ifdef __cplusplus 29 extern "C" { 30 #endif 31 32 /* RSS PPC names */ 33 enum ppc_rss_name_t { 34 PPC_RSS_MAIN0 = 0, /*!< MAIN PPC 0 */ 35 PPC_RSS_MAIN_EXP0, /*!< Expansion 0 MAIN PPC */ 36 PPC_RSS_MAIN_EXP1, /*!< Expansion 1 MAIN PPC */ 37 PPC_RSS_MAIN_EXP2, /*!< Expansion 2 MAIN PPC */ 38 PPC_RSS_MAIN_EXP3, /*!< Expansion 3 MAIN PPC */ 39 PPC_RSS_PERIPH0, /*!< PERIPH PPC0 */ 40 PPC_RSS_PERIPH1, /*!< PERIPH PPC1 */ 41 PPC_RSS_PERIPH_EXP0, /*!< Expansion 0 PERIPH PPC */ 42 PPC_RSS_PERIPH_EXP1, /*!< Expansion 1 PERIPH PPC */ 43 PPC_RSS_PERIPH_EXP2, /*!< Expansion 2 PERIPH PPC */ 44 PPC_RSS_PERIPH_EXP3, /*!< Expansion 3 PERIPH PPC */ 45 RSS_PPC_MAX_NUM 46 }; 47 48 /* RSS PPC device configuration structure */ 49 struct ppc_rss_dev_cfg_t { 50 uint32_t const sacfg_base; /*!< Secure Privilege Control Block base */ 51 uint32_t const nsacfg_base; /*!< Non-Secure Privilege Control Block base */ 52 enum ppc_rss_name_t ppc_name; 53 }; 54 55 /* RSS PPC device data structure */ 56 struct ppc_rss_dev_data_t { 57 volatile uint32_t* sacfg_ns_ppc; /*!< Pointer to non-secure register */ 58 volatile uint32_t* sacfg_sp_ppc; /*!< Pointer to secure unprivileged 59 register */ 60 volatile uint32_t* nsacfg_nsp_ppc; /*!< Pointer to non-secure unprivileged 61 register */ 62 uint32_t int_bit_mask; /*!< Interrupt bit mask */ 63 bool is_initialized; /*!< Indicates if the PPC driver 64 is initialized */ 65 }; 66 67 /* RSS PPC device structure */ 68 struct ppc_rss_dev_t { 69 const struct ppc_rss_dev_cfg_t* const cfg; /*!< PPC configuration */ 70 struct ppc_rss_dev_data_t* const data; /*!< PPC data */ 71 }; 72 73 /* Security attribute used to configure the peripherals */ 74 enum ppc_rss_sec_attr_t { 75 PPC_RSS_SECURE_ACCESS = 0, /*! Secure access */ 76 PPC_RSS_NONSECURE_ACCESS, /*! Non-secure access */ 77 }; 78 79 /* Privilege attribute used to configure the peripherals */ 80 enum ppc_rss_priv_attr_t { 81 PPC_RSS_PRIV_AND_NONPRIV_ACCESS = 0, /*! Privilege and NonPrivilege 82 access */ 83 PPC_RSS_PRIV_ONLY_ACCESS, /*! Privilege only access */ 84 }; 85 86 /* ARM PPC error codes */ 87 enum ppc_rss_error_t { 88 PPC_RSS_ERR_NONE = 0, /*!< No error */ 89 PPC_RSS_ERR_INVALID_PARAM, /*!< PPC invalid parameter error */ 90 PPC_RSS_ERR_NOT_INIT, /*!< PPC not initialized */ 91 PPC_RSS_ERR_NOT_PERMITTED /*!< PPC Operation not permitted */ 92 }; 93 94 /** 95 * \brief Initialize the PPC device. 96 * 97 * \param[in] dev PPC device \ref ppc_rss_dev_t 98 * 99 * \return Returns error code as specified in \ref ppc_rss_error_t 100 * 101 * \note This function doesn't check if dev is NULL. 102 */ 103 enum ppc_rss_error_t ppc_rss_init(struct ppc_rss_dev_t* dev); 104 105 /** 106 * \brief Configures privilege attribute through the PPC device. 107 * 108 * \param[in] dev PPC device \ref ppc_rss_dev_t 109 * \param[in] mask Peripheral mask for the PPC. 110 * \param[in] sec_attr Secure attribute value. 111 * \param[in] priv_attr Privilege attribute value. 112 * 113 * \return Returns error code as specified in \ref ppc_rss_error_t 114 * 115 * \note This function doesn't check if dev is NULL. 116 */ 117 enum ppc_rss_error_t 118 ppc_rss_config_privilege(struct ppc_rss_dev_t* dev, uint32_t mask, 119 enum ppc_rss_sec_attr_t sec_attr, 120 enum ppc_rss_priv_attr_t priv_attr); 121 122 /** 123 * \brief Checks if the peripheral is configured as Privilege only or 124 * Privilege and non-Privilege access mode. 125 * 126 * \param[in] dev PPC device \ref ppc_rss_dev_t 127 * \param[in] mask Peripheral mask for the PPC. 128 * 129 * \return Returns true for Privilege only configuration and false otherwise 130 * - with non-secure caller in the non-secure domain 131 * - with secure caller in the configured security domain 132 * If the driver is not initialized the return value of this function is 133 * true (Privilege only) as it is the default system configuration. 134 * 135 * \note This function doesn't check if dev is NULL. 136 */ 137 bool ppc_rss_is_periph_priv_only(struct ppc_rss_dev_t* dev, 138 uint32_t mask); 139 140 /* Secure only functions */ 141 #if (defined (__ARM_FEATURE_CMSE) && (__ARM_FEATURE_CMSE == 3U)) 142 143 /** 144 * \brief Configures security attribute through the PPC device. 145 * 146 * \param[in] dev PPC device \ref ppc_rss_dev_t 147 * \param[in] mask Peripheral mask for the PPC. 148 * \param[in] sec_attr Secure attribute value. 149 * 150 * \return Returns error code as specified in \ref ppc_rss_error_t 151 * 152 * \note This function doesn't check if dev is NULL. 153 */ 154 enum ppc_rss_error_t 155 ppc_rss_config_security(struct ppc_rss_dev_t* dev, uint32_t mask, 156 enum ppc_rss_sec_attr_t sec_attr); 157 158 /** 159 * \brief Checks if the peripheral is configured as secure or non-secure. 160 * 161 * \param[in] dev PPC device \ref ppc_rss_dev_t 162 * \param[in] mask Peripheral mask for the PPC. 163 * 164 * \return Returns true for secure and false for non-secure. 165 * If the driver is not initalized the return value is true (secure) as 166 * it is the default system configuration. 167 * 168 * \note This function doesn't check if dev is NULL. 169 */ 170 bool ppc_rss_is_periph_secure(struct ppc_rss_dev_t* dev, 171 uint32_t mask); 172 173 /** 174 * \brief Enables PPC interrupt. 175 * 176 * \param[in] dev PPC device \ref ppc_rss_dev_t 177 * 178 * \return Returns error code as specified in \ref ppc_rss_error_t 179 * 180 * \note This function doesn't check if dev is NULL. 181 */ 182 enum ppc_rss_error_t ppc_rss_irq_enable(struct ppc_rss_dev_t* dev); 183 184 /** 185 * \brief Disables PPC interrupt. 186 * 187 * \param[in] dev PPC device \ref ppc_rss_dev_t 188 * 189 * \note This function doesn't check if dev is NULL. 190 */ 191 void ppc_rss_irq_disable(struct ppc_rss_dev_t* dev); 192 193 /** 194 * \brief Clears PPC interrupt. 195 * 196 * \param[in] dev PPC device \ref ppc_rss_dev_t 197 * 198 * \note This function doesn't check if dev is NULL. 199 */ 200 void ppc_rss_clear_irq(struct ppc_rss_dev_t* dev); 201 202 /** 203 * \brief Returns the PPC interrupt state. 204 * 205 * \param[in] dev PPC device \ref ppc_rss_dev_t 206 * 207 * \return Returns true if the interrupt is active and otherwise false. 208 * If the driver is not initalized the return value of this function is 209 * false (not active) as it is the default system configuration. 210 * 211 * \note This function doesn't check if dev is NULL. 212 */ 213 bool ppc_rss_irq_state(struct ppc_rss_dev_t* dev); 214 215 #endif /* (defined (__ARM_FEATURE_CMSE) && (__ARM_FEATURE_CMSE == 3U)) */ 216 217 #ifdef __cplusplus 218 } 219 #endif 220 #endif /* __PPC_RSS_DRV_H__ */ 221