1 /* 2 * Arm SCP/MCP Software 3 * Copyright (c) 2022, Arm Limited and Contributors. All rights reserved. 4 * 5 * SPDX-License-Identifier: BSD-3-Clause 6 * 7 * Description: 8 * Message Handling Unit (MHU) v3 Device Driver. 9 */ 10 11 #ifndef MOD_MHU3_H 12 #define MOD_MHU3_H 13 14 #include <fwk_macros.h> 15 16 #include <stdint.h> 17 18 #define SCP_MHU3_PBX_MBX_SIZE (64 * 1024) 19 20 /* Mask to apply to MBX_FCH_CTRL to enable Fast Channel Mailbox interrupts */ 21 #define SCP_MHU3_MBX_INT_EN (4U) 22 23 /*! 24 * \addtogroup GroupModules Modules 25 * \{ 26 */ 27 28 /*! 29 * \defgroup GroupMHUv3 Message Handling Unit (MHU) v3 Driver 30 * \{ 31 */ 32 33 /*! \brief MHU v3 Channel Types */ 34 enum mod_mhu3_channel_type { 35 /*! Doorbell channel type */ 36 MOD_MHU3_CHANNEL_TYPE_DBCH, 37 /* Fast channel type */ 38 MOD_MHU3_CHANNEL_TYPE_FCH, 39 }; 40 41 /*! 42 * \brief API indices 43 */ 44 enum mod_mhu3_api_idx { 45 #ifdef BUILD_HAS_MOD_TRANSPORT 46 /*! TRANSPORT driver API */ 47 MOD_MHU3_API_IDX_TRANSPORT_DRIVER, 48 #endif 49 /*! MHU3 API count */ 50 MOD_MHU3_API_IDX_COUNT, 51 }; 52 53 /*! \brief Doorbell channel configuration 54 * 55 * \details In MHU3 we can have up to 128 doorbell channels and each 56 * channel can represent 32 independent events indicated 57 * by a flag within the doorbell register. 58 * Hence in MHU3 a channel is represented by its MBX and PBX 59 * number(s) (e.g SCP -> AP) and the position of the event flags 60 */ 61 struct mod_mhu3_dbch_config { 62 /*! PBX channel number */ 63 uint32_t pbx_channel : 8; 64 /*! 65 * Each doorbell channel has 32 bits which represents 66 * 32 independent 'events' per doorbell channel 67 * flag_pos indicates position of the bit(flag) within doorbell 68 * register on which this channel is expected to send or 69 * receive communication. 70 */ 71 uint32_t pbx_flag_pos : 8; 72 73 /*! MBX channel number */ 74 uint32_t mbx_channel : 8; 75 /*! MBX flag position within channel */ 76 uint32_t mbx_flag_pos : 8; 77 }; 78 79 /*! 80 * \brief Fast channel direction, Fast Channels are unidirectional 81 */ 82 enum mod_fch_direction { 83 /*! Direction in: Channel used by this processor to receive messages */ 84 MOD_MHU3_FCH_DIR_IN, 85 /*! Direction out: Channel used by this processor to send messages */ 86 MOD_MHU3_FCH_DIR_OUT, 87 /*! Direction count */ 88 MOD_MHU3_FCH_DIR_COUNT, 89 }; 90 91 /*! \brief Fast channel configuration 92 * 93 * \details In MHU3 the number of Fast Channels that can be supported is 94 * configurable between: 95 * * 1-1024 when the Fast Channel word-size is 32 bits. 96 * * 1-512 when the Fast Channel word-size is 64 bits. 97 * Due to the possible number of Fast Channels, they are controlled in 98 * groups called Fast Channel Groups. There can be between 1 and 32 Fast 99 * Channel Groups in a Postbox or Mailbox each containing between 1 and 32 100 * Fast Channels. 101 */ 102 struct mod_mhu3_fc_config { 103 /*! 104 * Fast Channel idx: 105 * offset of the word in PFCW<n>_PAY 106 * e.g for 107 * idx 0 is PFCW_PAY + (0 * 4) 108 * idx 1 is PFCW_PAY + (1 * 4) 109 * grup_num marks the end of the group 110 * e.g. 111 * for idx 0 & grup_num 2 it 112 * is PCFW_PAY + (0 * 4) to PCFW_PAY + (0 * 4 + 4 * 2) 113 */ 114 uint16_t idx; 115 /*! Fast Channel Group number for the given Fast Channel 116 * There can be between 1-32 Fast Channel Groups. 117 */ 118 uint8_t grp_num; 119 /*! Fast Channel Direction */ 120 enum mod_fch_direction direction; 121 }; 122 123 /*! \brief Configuration of a channel between MHU(S/R) <=> MHU(R/S) 124 * 125 * \details Each MHU v3 channel is identified using its type 126 * e.g. Doorbell channel or Fast Channel (see ::mod_mhu3_channel_type) 127 * Each channel includes its associated channel information e.g. 128 * in doorbell channel it will be represented by a PBX channel number, its 129 * flag position within corresponding PBX channel, MBX channel number and 130 * its flag position within corresponding MBX channel. 131 */ 132 struct mod_mhu3_channel_config { 133 /*! Type of the MHU channel */ 134 enum mod_mhu3_channel_type type; 135 /*! Configuration of the specified channel type */ 136 union { 137 /*! Doorbell channel configuration */ 138 struct mod_mhu3_dbch_config dbch; 139 /*! Fast channel configuration */ 140 struct mod_mhu3_fc_config fch; 141 }; 142 }; 143 144 /*! 145 * \brief MHU v3 device 146 * 147 * \details Abstract representation of a bidirectional MHU device that consists 148 * of a single receive interrupt line and channel configuration. 149 */ 150 struct mod_mhu3_device_config { 151 /*! IRQ number of the receive interrupt line */ 152 unsigned int irq; 153 154 /*! Base address of the registers of the incoming MHU, MBX 155 * (base address of the paired PBX on the target with current processor) 156 */ 157 uintptr_t in; 158 159 /*! Base address of the registers of the outgoing MHU, PBX 160 * (base address of the paired MBX on the target with current processor) 161 */ 162 uintptr_t out; 163 164 /*! Base address of the registers of the incoming MHU, MBX 165 * (as seen by the firmware/OS running on the target processor) 166 */ 167 uintptr_t in_target; 168 169 /*! Base address of the registers of the outgoing MHU, PBX 170 * (as seen by the firmware/OS running on the target processor) 171 */ 172 uintptr_t out_target; 173 174 /*! Channel configuration array */ 175 struct mod_mhu3_channel_config *channels; 176 }; 177 178 /*! 179 * \brief Build an MHU v3 Doorbell channel configuration 180 * 181 * \note This macro expands to a designated channel configuration, and can be 182 * used to initialize a ::mod_mhu3_channel_config. 183 * 184 * \details Example usage: 185 * \code{.c} 186 * struct mod_mhu3_channel_config ch = MOD_MHU3_INIT_DBCH(0, 1, 0, 1) 187 * \endcode 188 * 189 * \param PBX_CH_NUMBER PostBox channel number. 190 * \param PBX_FLAG_POS PostBox flag position. 191 * \param MBX_CH_NUMBER Mailbox channel number. 192 * \param MBX_FLAG_POS Mailbox flag position. 193 * 194 * \return Element identifier. 195 */ 196 #define MOD_MHU3_INIT_DBCH( \ 197 PBX_CH_NUMBER, PBX_FLAG_POS, MBX_CH_NUMBER, MBX_FLAG_POS) \ 198 { \ 199 .type = MOD_MHU3_CHANNEL_TYPE_DBCH, \ 200 { \ 201 .dbch = { \ 202 .pbx_channel = PBX_CH_NUMBER, \ 203 .pbx_flag_pos = PBX_FLAG_POS, \ 204 .mbx_channel = MBX_CH_NUMBER, \ 205 .mbx_flag_pos = MBX_FLAG_POS, \ 206 }, \ 207 } \ 208 } 209 210 /*! 211 * \brief Build an MHU v3 Fast channel configuration 212 * 213 * \note This macro expands to a designated fast channel configuration, 214 * and can be used to initialize a ::mod_mhu3_channel_config. 215 * 216 * \details Example usage: 217 * \code{.c} 218 * struct mod_mhu3_channel_config ch = MOD_MHU3_INIT_FCH(0, 1, 0) 219 * \endcode 220 * 221 * \param FCH_IDX Channel number. 222 * \param FCH_GROUP_NUM Fast Channel Group number for the given Fast Channel. 223 * \param FCH_DIRECTION Fast Channel direction in or out. 224 * 225 * \return Element identifier. 226 */ 227 #define MOD_MHU3_INIT_FCH(FCH_IDX, FCH_GROUP_NUM, FCH_DIRECTION) \ 228 { \ 229 .type = MOD_MHU3_CHANNEL_TYPE_FCH, \ 230 { \ 231 .fch = { \ 232 .idx = FCH_IDX, \ 233 .grp_num = FCH_GROUP_NUM, \ 234 .direction = FCH_DIRECTION, \ 235 }, \ 236 } \ 237 } 238 239 /*! 240 * \} 241 */ 242 243 /*! 244 * \} 245 */ 246 247 #endif /* MOD_MHU3_H */ 248