1104 lines · c
1// SPDX-License-Identifier: GPL-2.02/*3 * ARM Message Handling Unit Version 3 (MHUv3) driver.4 *5 * Copyright (C) 2024 ARM Ltd.6 *7 * Based on ARM MHUv2 driver.8 */9 10#include <linux/bitfield.h>11#include <linux/bitops.h>12#include <linux/bits.h>13#include <linux/cleanup.h>14#include <linux/device.h>15#include <linux/interrupt.h>16#include <linux/mailbox_controller.h>17#include <linux/module.h>18#include <linux/of_address.h>19#include <linux/platform_device.h>20#include <linux/spinlock.h>21#include <linux/sizes.h>22#include <linux/slab.h>23#include <linux/types.h>24 25/* ====== MHUv3 Registers ====== */26 27/* Maximum number of Doorbell channel windows */28#define MHUV3_DBCW_MAX 12829/* Number of DBCH combined interrupt status registers */30#define MHUV3_DBCH_CMB_INT_ST_REG_CNT 431 32/* Number of FFCH combined interrupt status registers */33#define MHUV3_FFCH_CMB_INT_ST_REG_CNT 234 35#define MHUV3_FLAG_BITS 3236 37/* Not a typo ... */38#define MHUV3_MAJOR_VERSION 239 40enum {41 MHUV3_MBOX_CELL_TYPE,42 MHUV3_MBOX_CELL_CHWN,43 MHUV3_MBOX_CELL_PARAM,44 MHUV3_MBOX_CELLS45};46 47/* Padding bitfields/fields represents hole in the regs MMIO */48 49/* CTRL_Page */50struct blk_id {51#define id GENMASK(3, 0)52 u32 val;53} __packed;54 55struct feat_spt0 {56#define dbe_spt GENMASK(3, 0)57#define fe_spt GENMASK(7, 4)58#define fce_spt GENMASK(11, 8)59 u32 val;60} __packed;61 62struct feat_spt1 {63#define auto_op_spt GENMASK(3, 0)64 u32 val;65} __packed;66 67struct dbch_cfg0 {68#define num_dbch GENMASK(7, 0)69 u32 val;70} __packed;71 72struct ffch_cfg0 {73#define num_ffch GENMASK(7, 0)74#define x8ba_spt BIT(8)75#define x16ba_spt BIT(9)76#define x32ba_spt BIT(10)77#define x64ba_spt BIT(11)78#define ffch_depth GENMASK(25, 16)79 u32 val;80} __packed;81 82struct fch_cfg0 {83#define num_fch GENMASK(9, 0)84#define fcgi_spt BIT(10) // MBX-only85#define num_fcg GENMASK(15, 11)86#define num_fch_per_grp GENMASK(20, 16)87#define fch_ws GENMASK(28, 21)88 u32 val;89} __packed;90 91struct ctrl {92#define op_req BIT(0)93#define ch_op_mask BIT(1)94 u32 val;95} __packed;96 97struct fch_ctrl {98#define _int_en BIT(2)99 u32 val;100} __packed;101 102struct iidr {103#define implementer GENMASK(11, 0)104#define revision GENMASK(15, 12)105#define variant GENMASK(19, 16)106#define product_id GENMASK(31, 20)107 u32 val;108} __packed;109 110struct aidr {111#define arch_minor_rev GENMASK(3, 0)112#define arch_major_rev GENMASK(7, 4)113 u32 val;114} __packed;115 116struct ctrl_page {117 struct blk_id blk_id;118 u8 pad[12];119 struct feat_spt0 feat_spt0;120 struct feat_spt1 feat_spt1;121 u8 pad1[8];122 struct dbch_cfg0 dbch_cfg0;123 u8 pad2[12];124 struct ffch_cfg0 ffch_cfg0;125 u8 pad3[12];126 struct fch_cfg0 fch_cfg0;127 u8 pad4[188];128 struct ctrl x_ctrl;129 /*-- MBX-only registers --*/130 u8 pad5[60];131 struct fch_ctrl fch_ctrl;132 u32 fcg_int_en;133 u8 pad6[696];134 /*-- End of MBX-only ---- */135 u32 dbch_int_st[MHUV3_DBCH_CMB_INT_ST_REG_CNT];136 u32 ffch_int_st[MHUV3_FFCH_CMB_INT_ST_REG_CNT];137 /*-- MBX-only registers --*/138 u8 pad7[88];139 u32 fcg_int_st;140 u8 pad8[12];141 u32 fcg_grp_int_st[32];142 u8 pad9[2760];143 /*-- End of MBX-only ---- */144 struct iidr iidr;145 struct aidr aidr;146 u32 imp_def_id[12];147} __packed;148 149/* DBCW_Page */150 151struct xbcw_ctrl {152#define comb_en BIT(0)153 u32 val;154} __packed;155 156struct pdbcw_int {157#define tfr_ack BIT(0)158 u32 val;159} __packed;160 161struct pdbcw_page {162 u32 st;163 u8 pad[8];164 u32 set;165 struct pdbcw_int int_st;166 struct pdbcw_int int_clr;167 struct pdbcw_int int_en;168 struct xbcw_ctrl ctrl;169} __packed;170 171struct mdbcw_page {172 u32 st;173 u32 st_msk;174 u32 clr;175 u8 pad[4];176 u32 msk_st;177 u32 msk_set;178 u32 msk_clr;179 struct xbcw_ctrl ctrl;180} __packed;181 182struct dummy_page {183 u8 pad[SZ_4K];184} __packed;185 186struct mhu3_pbx_frame_reg {187 struct ctrl_page ctrl;188 struct pdbcw_page dbcw[MHUV3_DBCW_MAX];189 struct dummy_page ffcw;190 struct dummy_page fcw;191 u8 pad[SZ_4K * 11];192 struct dummy_page impdef;193} __packed;194 195struct mhu3_mbx_frame_reg {196 struct ctrl_page ctrl;197 struct mdbcw_page dbcw[MHUV3_DBCW_MAX];198 struct dummy_page ffcw;199 struct dummy_page fcw;200 u8 pad[SZ_4K * 11];201 struct dummy_page impdef;202} __packed;203 204/* Macro for reading a bitmask within a physically mapped packed struct */205#define readl_relaxed_bitmask(_regptr, _bitmask) \206 ({ \207 unsigned long _rval; \208 _rval = readl_relaxed(_regptr); \209 FIELD_GET(_bitmask, _rval); \210 })211 212/* Macro for writing a bitmask within a physically mapped packed struct */213#define writel_relaxed_bitmask(_value, _regptr, _bitmask) \214 ({ \215 unsigned long _rval; \216 typeof(_regptr) _rptr = _regptr; \217 typeof(_bitmask) _bmask = _bitmask; \218 _rval = readl_relaxed(_rptr); \219 _rval &= ~(_bmask); \220 _rval |= FIELD_PREP((unsigned long long)_bmask, _value);\221 writel_relaxed(_rval, _rptr); \222 })223 224/* ====== MHUv3 data structures ====== */225 226enum mhuv3_frame {227 PBX_FRAME,228 MBX_FRAME,229};230 231static char *mhuv3_str[] = {232 "PBX",233 "MBX"234};235 236enum mhuv3_extension_type {237 DBE_EXT,238 FCE_EXT,239 FE_EXT,240 NUM_EXT241};242 243static char *mhuv3_ext_str[] = {244 "DBE",245 "FCE",246 "FE"247};248 249struct mhuv3;250 251/**252 * struct mhuv3_protocol_ops - MHUv3 operations253 *254 * @rx_startup: Receiver startup callback.255 * @rx_shutdown: Receiver shutdown callback.256 * @read_data: Read available Sender in-band LE data (if any).257 * @rx_complete: Acknowledge data reception to the Sender. Any out-of-band data258 * has to have been already retrieved before calling this.259 * @tx_startup: Sender startup callback.260 * @tx_shutdown: Sender shutdown callback.261 * @last_tx_done: Report back to the Sender if the last transfer has completed.262 * @send_data: Send data to the receiver.263 *264 * Each supported transport protocol provides its own implementation of265 * these operations.266 */267struct mhuv3_protocol_ops {268 int (*rx_startup)(struct mhuv3 *mhu, struct mbox_chan *chan);269 void (*rx_shutdown)(struct mhuv3 *mhu, struct mbox_chan *chan);270 void *(*read_data)(struct mhuv3 *mhu, struct mbox_chan *chan);271 void (*rx_complete)(struct mhuv3 *mhu, struct mbox_chan *chan);272 void (*tx_startup)(struct mhuv3 *mhu, struct mbox_chan *chan);273 void (*tx_shutdown)(struct mhuv3 *mhu, struct mbox_chan *chan);274 int (*last_tx_done)(struct mhuv3 *mhu, struct mbox_chan *chan);275 int (*send_data)(struct mhuv3 *mhu, struct mbox_chan *chan, void *arg);276};277 278/**279 * struct mhuv3_mbox_chan_priv - MHUv3 channel private information280 *281 * @ch_idx: Channel window index associated to this mailbox channel.282 * @doorbell: Doorbell bit number within the @ch_idx window.283 * Only relevant to Doorbell transport.284 * @ops: Transport protocol specific operations for this channel.285 *286 * Transport specific data attached to mmailbox channel priv data.287 */288struct mhuv3_mbox_chan_priv {289 u32 ch_idx;290 u32 doorbell;291 const struct mhuv3_protocol_ops *ops;292};293 294/**295 * struct mhuv3_extension - MHUv3 extension descriptor296 *297 * @type: Type of extension298 * @num_chans: Max number of channels found for this extension.299 * @base_ch_idx: First channel number assigned to this extension, picked from300 * the set of all mailbox channels descriptors created.301 * @mbox_of_xlate: Extension specific helper to parse DT and lookup associated302 * channel from the related 'mboxes' property.303 * @combined_irq_setup: Extension specific helper to setup the combined irq.304 * @channels_init: Extension specific helper to initialize channels.305 * @chan_from_comb_irq_get: Extension specific helper to lookup which channel306 * triggered the combined irq.307 * @pending_db: Array of per-channel pending doorbells.308 * @pending_lock: Protect access to pending_db.309 */310struct mhuv3_extension {311 enum mhuv3_extension_type type;312 unsigned int num_chans;313 unsigned int base_ch_idx;314 struct mbox_chan *(*mbox_of_xlate)(struct mhuv3 *mhu,315 unsigned int channel,316 unsigned int param);317 void (*combined_irq_setup)(struct mhuv3 *mhu);318 int (*channels_init)(struct mhuv3 *mhu);319 struct mbox_chan *(*chan_from_comb_irq_get)(struct mhuv3 *mhu);320 u32 pending_db[MHUV3_DBCW_MAX];321 /* Protect access to pending_db */322 spinlock_t pending_lock;323};324 325/**326 * struct mhuv3 - MHUv3 mailbox controller data327 *328 * @frame: Frame type: MBX_FRAME or PBX_FRAME.329 * @auto_op_full: Flag to indicate if the MHU supports AutoOp full mode.330 * @major: MHUv3 controller architectural major version.331 * @minor: MHUv3 controller architectural minor version.332 * @implem: MHUv3 controller IIDR implementer.333 * @rev: MHUv3 controller IIDR revision.334 * @var: MHUv3 controller IIDR variant.335 * @prod_id: MHUv3 controller IIDR product_id.336 * @num_chans: The total number of channnels discovered across all extensions.337 * @cmb_irq: Combined IRQ number if any found defined.338 * @ctrl: A reference to the MHUv3 control page for this block.339 * @pbx: Base address of the PBX register mapping region.340 * @mbx: Base address of the MBX register mapping region.341 * @ext: Array holding descriptors for any found implemented extension.342 * @mbox: Mailbox controller belonging to the MHU frame.343 */344struct mhuv3 {345 enum mhuv3_frame frame;346 bool auto_op_full;347 unsigned int major;348 unsigned int minor;349 unsigned int implem;350 unsigned int rev;351 unsigned int var;352 unsigned int prod_id;353 unsigned int num_chans;354 int cmb_irq;355 struct ctrl_page __iomem *ctrl;356 union {357 struct mhu3_pbx_frame_reg __iomem *pbx;358 struct mhu3_mbx_frame_reg __iomem *mbx;359 };360 struct mhuv3_extension *ext[NUM_EXT];361 struct mbox_controller mbox;362};363 364#define mhu_from_mbox(_mbox) container_of(_mbox, struct mhuv3, mbox)365 366typedef int (*mhuv3_extension_initializer)(struct mhuv3 *mhu);367 368/* =================== Doorbell transport protocol operations =============== */369 370static void mhuv3_doorbell_tx_startup(struct mhuv3 *mhu, struct mbox_chan *chan)371{372 struct mhuv3_mbox_chan_priv *priv = chan->con_priv;373 374 /* Enable Transfer Acknowledgment events */375 writel_relaxed_bitmask(0x1, &mhu->pbx->dbcw[priv->ch_idx].int_en, tfr_ack);376}377 378static void mhuv3_doorbell_tx_shutdown(struct mhuv3 *mhu, struct mbox_chan *chan)379{380 struct mhuv3_mbox_chan_priv *priv = chan->con_priv;381 struct mhuv3_extension *e = mhu->ext[DBE_EXT];382 unsigned long flags;383 384 /* Disable Channel Transfer Ack events */385 writel_relaxed_bitmask(0x0, &mhu->pbx->dbcw[priv->ch_idx].int_en, tfr_ack);386 387 /* Clear Channel Transfer Ack and pending doorbells */388 writel_relaxed_bitmask(0x1, &mhu->pbx->dbcw[priv->ch_idx].int_clr, tfr_ack);389 spin_lock_irqsave(&e->pending_lock, flags);390 e->pending_db[priv->ch_idx] = 0;391 spin_unlock_irqrestore(&e->pending_lock, flags);392}393 394static int mhuv3_doorbell_rx_startup(struct mhuv3 *mhu, struct mbox_chan *chan)395{396 struct mhuv3_mbox_chan_priv *priv = chan->con_priv;397 398 /* Unmask Channel Transfer events */399 writel_relaxed(BIT(priv->doorbell), &mhu->mbx->dbcw[priv->ch_idx].msk_clr);400 401 return 0;402}403 404static void mhuv3_doorbell_rx_shutdown(struct mhuv3 *mhu,405 struct mbox_chan *chan)406{407 struct mhuv3_mbox_chan_priv *priv = chan->con_priv;408 409 /* Mask Channel Transfer events */410 writel_relaxed(BIT(priv->doorbell), &mhu->mbx->dbcw[priv->ch_idx].msk_set);411}412 413static void mhuv3_doorbell_rx_complete(struct mhuv3 *mhu, struct mbox_chan *chan)414{415 struct mhuv3_mbox_chan_priv *priv = chan->con_priv;416 417 /* Clearing the pending transfer generates the Channel Transfer Ack */418 writel_relaxed(BIT(priv->doorbell), &mhu->mbx->dbcw[priv->ch_idx].clr);419}420 421static int mhuv3_doorbell_last_tx_done(struct mhuv3 *mhu,422 struct mbox_chan *chan)423{424 struct mhuv3_mbox_chan_priv *priv = chan->con_priv;425 int done;426 427 done = !(readl_relaxed(&mhu->pbx->dbcw[priv->ch_idx].st) &428 BIT(priv->doorbell));429 if (done) {430 struct mhuv3_extension *e = mhu->ext[DBE_EXT];431 unsigned long flags;432 433 /* Take care to clear the pending doorbell also when polling */434 spin_lock_irqsave(&e->pending_lock, flags);435 e->pending_db[priv->ch_idx] &= ~BIT(priv->doorbell);436 spin_unlock_irqrestore(&e->pending_lock, flags);437 }438 439 return done;440}441 442static int mhuv3_doorbell_send_data(struct mhuv3 *mhu, struct mbox_chan *chan,443 void *arg)444{445 struct mhuv3_mbox_chan_priv *priv = chan->con_priv;446 struct mhuv3_extension *e = mhu->ext[DBE_EXT];447 448 scoped_guard(spinlock_irqsave, &e->pending_lock) {449 /* Only one in-flight Transfer is allowed per-doorbell */450 if (e->pending_db[priv->ch_idx] & BIT(priv->doorbell))451 return -EBUSY;452 453 e->pending_db[priv->ch_idx] |= BIT(priv->doorbell);454 }455 456 writel_relaxed(BIT(priv->doorbell), &mhu->pbx->dbcw[priv->ch_idx].set);457 458 return 0;459}460 461static const struct mhuv3_protocol_ops mhuv3_doorbell_ops = {462 .tx_startup = mhuv3_doorbell_tx_startup,463 .tx_shutdown = mhuv3_doorbell_tx_shutdown,464 .rx_startup = mhuv3_doorbell_rx_startup,465 .rx_shutdown = mhuv3_doorbell_rx_shutdown,466 .rx_complete = mhuv3_doorbell_rx_complete,467 .last_tx_done = mhuv3_doorbell_last_tx_done,468 .send_data = mhuv3_doorbell_send_data,469};470 471/* Sender and receiver mailbox ops */472static bool mhuv3_sender_last_tx_done(struct mbox_chan *chan)473{474 struct mhuv3_mbox_chan_priv *priv = chan->con_priv;475 struct mhuv3 *mhu = mhu_from_mbox(chan->mbox);476 477 return priv->ops->last_tx_done(mhu, chan);478}479 480static int mhuv3_sender_send_data(struct mbox_chan *chan, void *data)481{482 struct mhuv3_mbox_chan_priv *priv = chan->con_priv;483 struct mhuv3 *mhu = mhu_from_mbox(chan->mbox);484 485 if (!priv->ops->last_tx_done(mhu, chan))486 return -EBUSY;487 488 return priv->ops->send_data(mhu, chan, data);489}490 491static int mhuv3_sender_startup(struct mbox_chan *chan)492{493 struct mhuv3_mbox_chan_priv *priv = chan->con_priv;494 struct mhuv3 *mhu = mhu_from_mbox(chan->mbox);495 496 if (priv->ops->tx_startup)497 priv->ops->tx_startup(mhu, chan);498 499 return 0;500}501 502static void mhuv3_sender_shutdown(struct mbox_chan *chan)503{504 struct mhuv3_mbox_chan_priv *priv = chan->con_priv;505 struct mhuv3 *mhu = mhu_from_mbox(chan->mbox);506 507 if (priv->ops->tx_shutdown)508 priv->ops->tx_shutdown(mhu, chan);509}510 511static const struct mbox_chan_ops mhuv3_sender_ops = {512 .send_data = mhuv3_sender_send_data,513 .startup = mhuv3_sender_startup,514 .shutdown = mhuv3_sender_shutdown,515 .last_tx_done = mhuv3_sender_last_tx_done,516};517 518static int mhuv3_receiver_startup(struct mbox_chan *chan)519{520 struct mhuv3_mbox_chan_priv *priv = chan->con_priv;521 struct mhuv3 *mhu = mhu_from_mbox(chan->mbox);522 523 return priv->ops->rx_startup(mhu, chan);524}525 526static void mhuv3_receiver_shutdown(struct mbox_chan *chan)527{528 struct mhuv3_mbox_chan_priv *priv = chan->con_priv;529 struct mhuv3 *mhu = mhu_from_mbox(chan->mbox);530 531 priv->ops->rx_shutdown(mhu, chan);532}533 534static int mhuv3_receiver_send_data(struct mbox_chan *chan, void *data)535{536 dev_err(chan->mbox->dev,537 "Trying to transmit on a MBX MHUv3 frame\n");538 return -EIO;539}540 541static bool mhuv3_receiver_last_tx_done(struct mbox_chan *chan)542{543 dev_err(chan->mbox->dev, "Trying to Tx poll on a MBX MHUv3 frame\n");544 return true;545}546 547static const struct mbox_chan_ops mhuv3_receiver_ops = {548 .send_data = mhuv3_receiver_send_data,549 .startup = mhuv3_receiver_startup,550 .shutdown = mhuv3_receiver_shutdown,551 .last_tx_done = mhuv3_receiver_last_tx_done,552};553 554static struct mbox_chan *mhuv3_dbe_mbox_of_xlate(struct mhuv3 *mhu,555 unsigned int channel,556 unsigned int doorbell)557{558 struct mhuv3_extension *e = mhu->ext[DBE_EXT];559 struct mbox_controller *mbox = &mhu->mbox;560 struct mbox_chan *chans = mbox->chans;561 562 if (channel >= e->num_chans || doorbell >= MHUV3_FLAG_BITS) {563 dev_err(mbox->dev, "Couldn't xlate to a valid channel (%d: %d)\n",564 channel, doorbell);565 return ERR_PTR(-ENODEV);566 }567 568 return &chans[e->base_ch_idx + channel * MHUV3_FLAG_BITS + doorbell];569}570 571static void mhuv3_dbe_combined_irq_setup(struct mhuv3 *mhu)572{573 struct mhuv3_extension *e = mhu->ext[DBE_EXT];574 int i;575 576 if (mhu->frame == PBX_FRAME) {577 struct pdbcw_page __iomem *dbcw = mhu->pbx->dbcw;578 579 for (i = 0; i < e->num_chans; i++) {580 writel_relaxed_bitmask(0x1, &dbcw[i].int_clr, tfr_ack);581 writel_relaxed_bitmask(0x0, &dbcw[i].int_en, tfr_ack);582 writel_relaxed_bitmask(0x1, &dbcw[i].ctrl, comb_en);583 }584 } else {585 struct mdbcw_page __iomem *dbcw = mhu->mbx->dbcw;586 587 for (i = 0; i < e->num_chans; i++) {588 writel_relaxed(0xFFFFFFFF, &dbcw[i].clr);589 writel_relaxed(0xFFFFFFFF, &dbcw[i].msk_set);590 writel_relaxed_bitmask(0x1, &dbcw[i].ctrl, comb_en);591 }592 }593}594 595static int mhuv3_dbe_channels_init(struct mhuv3 *mhu)596{597 struct mhuv3_extension *e = mhu->ext[DBE_EXT];598 struct mbox_controller *mbox = &mhu->mbox;599 struct mbox_chan *chans;600 int i;601 602 chans = mbox->chans + mbox->num_chans;603 e->base_ch_idx = mbox->num_chans;604 for (i = 0; i < e->num_chans; i++) {605 struct mhuv3_mbox_chan_priv *priv;606 int k;607 608 for (k = 0; k < MHUV3_FLAG_BITS; k++) {609 priv = devm_kmalloc(mbox->dev, sizeof(*priv), GFP_KERNEL);610 if (!priv)611 return -ENOMEM;612 613 priv->ch_idx = i;614 priv->ops = &mhuv3_doorbell_ops;615 priv->doorbell = k;616 chans++->con_priv = priv;617 mbox->num_chans++;618 }619 }620 621 spin_lock_init(&e->pending_lock);622 623 return 0;624}625 626static bool mhuv3_dbe_doorbell_lookup(struct mhuv3 *mhu, unsigned int channel,627 unsigned int *db)628{629 struct mhuv3_extension *e = mhu->ext[DBE_EXT];630 struct device *dev = mhu->mbox.dev;631 u32 st;632 633 if (mhu->frame == PBX_FRAME) {634 u32 active_dbs, fired_dbs;635 636 st = readl_relaxed_bitmask(&mhu->pbx->dbcw[channel].int_st,637 tfr_ack);638 if (!st)639 goto err_spurious;640 641 active_dbs = readl_relaxed(&mhu->pbx->dbcw[channel].st);642 scoped_guard(spinlock_irqsave, &e->pending_lock) {643 fired_dbs = e->pending_db[channel] & ~active_dbs;644 if (!fired_dbs)645 goto err_spurious;646 647 *db = __ffs(fired_dbs);648 e->pending_db[channel] &= ~BIT(*db);649 }650 fired_dbs &= ~BIT(*db);651 /* Clear TFR Ack if no more doorbells pending */652 if (!fired_dbs)653 writel_relaxed_bitmask(0x1,654 &mhu->pbx->dbcw[channel].int_clr,655 tfr_ack);656 } else {657 st = readl_relaxed(&mhu->mbx->dbcw[channel].st_msk);658 if (!st)659 goto err_spurious;660 661 *db = __ffs(st);662 }663 664 return true;665 666err_spurious:667 dev_warn(dev, "Spurious IRQ on %s channel:%d\n",668 mhuv3_str[mhu->frame], channel);669 670 return false;671}672 673static struct mbox_chan *mhuv3_dbe_chan_from_comb_irq_get(struct mhuv3 *mhu)674{675 struct mhuv3_extension *e = mhu->ext[DBE_EXT];676 struct device *dev = mhu->mbox.dev;677 int i;678 679 for (i = 0; i < MHUV3_DBCH_CMB_INT_ST_REG_CNT; i++) {680 unsigned int channel, db;681 u32 cmb_st;682 683 cmb_st = readl_relaxed(&mhu->ctrl->dbch_int_st[i]);684 if (!cmb_st)685 continue;686 687 channel = i * MHUV3_FLAG_BITS + __ffs(cmb_st);688 if (channel >= e->num_chans) {689 dev_err(dev, "Invalid %s channel:%d\n",690 mhuv3_str[mhu->frame], channel);691 return ERR_PTR(-EIO);692 }693 694 if (!mhuv3_dbe_doorbell_lookup(mhu, channel, &db))695 continue;696 697 dev_dbg(dev, "Found %s ch[%d]/db[%d]\n",698 mhuv3_str[mhu->frame], channel, db);699 700 return &mhu->mbox.chans[channel * MHUV3_FLAG_BITS + db];701 }702 703 return ERR_PTR(-EIO);704}705 706static int mhuv3_dbe_init(struct mhuv3 *mhu)707{708 struct device *dev = mhu->mbox.dev;709 struct mhuv3_extension *e;710 711 if (!readl_relaxed_bitmask(&mhu->ctrl->feat_spt0, dbe_spt))712 return 0;713 714 dev_dbg(dev, "%s: Initializing DBE Extension.\n", mhuv3_str[mhu->frame]);715 716 e = devm_kzalloc(dev, sizeof(*e), GFP_KERNEL);717 if (!e)718 return -ENOMEM;719 720 e->type = DBE_EXT;721 /* Note that, by the spec, the number of channels is (num_dbch + 1) */722 e->num_chans =723 readl_relaxed_bitmask(&mhu->ctrl->dbch_cfg0, num_dbch) + 1;724 e->mbox_of_xlate = mhuv3_dbe_mbox_of_xlate;725 e->combined_irq_setup = mhuv3_dbe_combined_irq_setup;726 e->channels_init = mhuv3_dbe_channels_init;727 e->chan_from_comb_irq_get = mhuv3_dbe_chan_from_comb_irq_get;728 729 mhu->num_chans += e->num_chans * MHUV3_FLAG_BITS;730 mhu->ext[DBE_EXT] = e;731 732 dev_dbg(dev, "%s: found %d DBE channels.\n",733 mhuv3_str[mhu->frame], e->num_chans);734 735 return 0;736}737 738static int mhuv3_fce_init(struct mhuv3 *mhu)739{740 struct device *dev = mhu->mbox.dev;741 742 if (!readl_relaxed_bitmask(&mhu->ctrl->feat_spt0, fce_spt))743 return 0;744 745 dev_dbg(dev, "%s: FCE Extension not supported by driver.\n",746 mhuv3_str[mhu->frame]);747 748 return 0;749}750 751static int mhuv3_fe_init(struct mhuv3 *mhu)752{753 struct device *dev = mhu->mbox.dev;754 755 if (!readl_relaxed_bitmask(&mhu->ctrl->feat_spt0, fe_spt))756 return 0;757 758 dev_dbg(dev, "%s: FE Extension not supported by driver.\n",759 mhuv3_str[mhu->frame]);760 761 return 0;762}763 764static mhuv3_extension_initializer mhuv3_extension_init[NUM_EXT] = {765 mhuv3_dbe_init,766 mhuv3_fce_init,767 mhuv3_fe_init,768};769 770static int mhuv3_initialize_channels(struct device *dev, struct mhuv3 *mhu)771{772 struct mbox_controller *mbox = &mhu->mbox;773 int i, ret = 0;774 775 mbox->chans = devm_kcalloc(dev, mhu->num_chans,776 sizeof(*mbox->chans), GFP_KERNEL);777 if (!mbox->chans)778 return dev_err_probe(dev, -ENOMEM,779 "Failed to initialize channels\n");780 781 for (i = 0; i < NUM_EXT && !ret; i++)782 if (mhu->ext[i])783 ret = mhu->ext[i]->channels_init(mhu);784 785 return ret;786}787 788static struct mbox_chan *mhuv3_mbox_of_xlate(struct mbox_controller *mbox,789 const struct of_phandle_args *pa)790{791 struct mhuv3 *mhu = mhu_from_mbox(mbox);792 unsigned int type, channel, param;793 794 if (pa->args_count != MHUV3_MBOX_CELLS)795 return ERR_PTR(-EINVAL);796 797 type = pa->args[MHUV3_MBOX_CELL_TYPE];798 if (type >= NUM_EXT)799 return ERR_PTR(-EINVAL);800 801 channel = pa->args[MHUV3_MBOX_CELL_CHWN];802 param = pa->args[MHUV3_MBOX_CELL_PARAM];803 804 return mhu->ext[type]->mbox_of_xlate(mhu, channel, param);805}806 807static void mhu_frame_cleanup_actions(void *data)808{809 struct mhuv3 *mhu = data;810 811 writel_relaxed_bitmask(0x0, &mhu->ctrl->x_ctrl, op_req);812}813 814static int mhuv3_frame_init(struct mhuv3 *mhu, void __iomem *regs)815{816 struct device *dev = mhu->mbox.dev;817 int i;818 819 mhu->ctrl = regs;820 mhu->frame = readl_relaxed_bitmask(&mhu->ctrl->blk_id, id);821 if (mhu->frame > MBX_FRAME)822 return dev_err_probe(dev, -EINVAL,823 "Invalid Frame type- %d\n", mhu->frame);824 825 mhu->major = readl_relaxed_bitmask(&mhu->ctrl->aidr, arch_major_rev);826 mhu->minor = readl_relaxed_bitmask(&mhu->ctrl->aidr, arch_minor_rev);827 mhu->implem = readl_relaxed_bitmask(&mhu->ctrl->iidr, implementer);828 mhu->rev = readl_relaxed_bitmask(&mhu->ctrl->iidr, revision);829 mhu->var = readl_relaxed_bitmask(&mhu->ctrl->iidr, variant);830 mhu->prod_id = readl_relaxed_bitmask(&mhu->ctrl->iidr, product_id);831 if (mhu->major != MHUV3_MAJOR_VERSION)832 return dev_err_probe(dev, -EINVAL,833 "Unsupported MHU %s block - major:%d minor:%d\n",834 mhuv3_str[mhu->frame], mhu->major,835 mhu->minor);836 837 mhu->auto_op_full =838 !!readl_relaxed_bitmask(&mhu->ctrl->feat_spt1, auto_op_spt);839 /* Request the PBX/MBX to remain operational */840 if (mhu->auto_op_full) {841 writel_relaxed_bitmask(0x1, &mhu->ctrl->x_ctrl, op_req);842 devm_add_action_or_reset(dev, mhu_frame_cleanup_actions, mhu);843 }844 845 dev_dbg(dev,846 "Found MHU %s block - major:%d minor:%d\n implem:0x%X rev:0x%X var:0x%X prod_id:0x%X",847 mhuv3_str[mhu->frame], mhu->major, mhu->minor,848 mhu->implem, mhu->rev, mhu->var, mhu->prod_id);849 850 if (mhu->frame == PBX_FRAME)851 mhu->pbx = regs;852 else853 mhu->mbx = regs;854 855 for (i = 0; i < NUM_EXT; i++) {856 int ret;857 858 /*859 * Note that extensions initialization fails only when such860 * extension initialization routine fails and the extensions861 * was found to be supported in hardware and in software.862 */863 ret = mhuv3_extension_init[i](mhu);864 if (ret)865 return dev_err_probe(dev, ret,866 "Failed to initialize %s %s\n",867 mhuv3_str[mhu->frame],868 mhuv3_ext_str[i]);869 }870 871 return 0;872}873 874static irqreturn_t mhuv3_pbx_comb_interrupt(int irq, void *arg)875{876 unsigned int i, found = 0;877 struct mhuv3 *mhu = arg;878 struct mbox_chan *chan;879 struct device *dev;880 int ret = IRQ_NONE;881 882 dev = mhu->mbox.dev;883 for (i = 0; i < NUM_EXT; i++) {884 struct mhuv3_mbox_chan_priv *priv;885 886 /* FCE does not participate to the PBX combined */887 if (i == FCE_EXT || !mhu->ext[i])888 continue;889 890 chan = mhu->ext[i]->chan_from_comb_irq_get(mhu);891 if (IS_ERR(chan))892 continue;893 894 found++;895 priv = chan->con_priv;896 if (!chan->cl) {897 dev_warn(dev, "TX Ack on UNBOUND channel (%u)\n",898 priv->ch_idx);899 continue;900 }901 902 mbox_chan_txdone(chan, 0);903 ret = IRQ_HANDLED;904 }905 906 if (found == 0)907 dev_warn_once(dev, "Failed to find channel for the TX interrupt\n");908 909 return ret;910}911 912static irqreturn_t mhuv3_mbx_comb_interrupt(int irq, void *arg)913{914 unsigned int i, found = 0;915 struct mhuv3 *mhu = arg;916 struct mbox_chan *chan;917 struct device *dev;918 int ret = IRQ_NONE;919 920 dev = mhu->mbox.dev;921 for (i = 0; i < NUM_EXT; i++) {922 struct mhuv3_mbox_chan_priv *priv;923 void *data __free(kfree) = NULL;924 925 if (!mhu->ext[i])926 continue;927 928 /* Process any extension which could be source of the IRQ */929 chan = mhu->ext[i]->chan_from_comb_irq_get(mhu);930 if (IS_ERR(chan))931 continue;932 933 found++;934 /* From here on we need to call rx_complete even on error */935 priv = chan->con_priv;936 if (!chan->cl) {937 dev_warn(dev, "RX Data on UNBOUND channel (%u)\n",938 priv->ch_idx);939 goto rx_ack;940 }941 942 /* Read optional in-band LE data first. */943 if (priv->ops->read_data) {944 data = priv->ops->read_data(mhu, chan);945 if (IS_ERR(data)) {946 dev_err(dev,947 "Failed to read in-band data. err:%ld\n",948 PTR_ERR(no_free_ptr(data)));949 goto rx_ack;950 }951 }952 953 mbox_chan_received_data(chan, data);954 ret = IRQ_HANDLED;955 956 /*957 * Acknowledge transfer after any possible optional958 * out-of-band data has also been retrieved via959 * mbox_chan_received_data().960 */961rx_ack:962 if (priv->ops->rx_complete)963 priv->ops->rx_complete(mhu, chan);964 }965 966 if (found == 0)967 dev_warn_once(dev, "Failed to find channel for the RX interrupt\n");968 969 return ret;970}971 972static int mhuv3_setup_pbx(struct mhuv3 *mhu)973{974 struct device *dev = mhu->mbox.dev;975 976 mhu->mbox.ops = &mhuv3_sender_ops;977 978 if (mhu->cmb_irq > 0) {979 int ret, i;980 981 ret = devm_request_threaded_irq(dev, mhu->cmb_irq, NULL,982 mhuv3_pbx_comb_interrupt,983 IRQF_ONESHOT, "mhuv3-pbx", mhu);984 if (ret)985 return dev_err_probe(dev, ret,986 "Failed to request PBX IRQ\n");987 988 mhu->mbox.txdone_irq = true;989 mhu->mbox.txdone_poll = false;990 991 for (i = 0; i < NUM_EXT; i++)992 if (mhu->ext[i])993 mhu->ext[i]->combined_irq_setup(mhu);994 995 dev_dbg(dev, "MHUv3 PBX IRQs initialized.\n");996 997 return 0;998 }999 1000 dev_info(dev, "Using PBX in Tx polling mode.\n");1001 mhu->mbox.txdone_irq = false;1002 mhu->mbox.txdone_poll = true;1003 mhu->mbox.txpoll_period = 1;1004 1005 return 0;1006}1007 1008static int mhuv3_setup_mbx(struct mhuv3 *mhu)1009{1010 struct device *dev = mhu->mbox.dev;1011 int ret, i;1012 1013 mhu->mbox.ops = &mhuv3_receiver_ops;1014 1015 if (mhu->cmb_irq <= 0)1016 return dev_err_probe(dev, -EINVAL,1017 "MBX combined IRQ is missing !\n");1018 1019 ret = devm_request_threaded_irq(dev, mhu->cmb_irq, NULL,1020 mhuv3_mbx_comb_interrupt, IRQF_ONESHOT,1021 "mhuv3-mbx", mhu);1022 if (ret)1023 return dev_err_probe(dev, ret, "Failed to request MBX IRQ\n");1024 1025 for (i = 0; i < NUM_EXT; i++)1026 if (mhu->ext[i])1027 mhu->ext[i]->combined_irq_setup(mhu);1028 1029 dev_dbg(dev, "MHUv3 MBX IRQs initialized.\n");1030 1031 return ret;1032}1033 1034static int mhuv3_irqs_init(struct mhuv3 *mhu, struct platform_device *pdev)1035{1036 dev_dbg(mhu->mbox.dev, "Initializing %s block.\n",1037 mhuv3_str[mhu->frame]);1038 1039 if (mhu->frame == PBX_FRAME) {1040 mhu->cmb_irq =1041 platform_get_irq_byname_optional(pdev, "combined");1042 return mhuv3_setup_pbx(mhu);1043 }1044 1045 mhu->cmb_irq = platform_get_irq_byname(pdev, "combined");1046 return mhuv3_setup_mbx(mhu);1047}1048 1049static int mhuv3_probe(struct platform_device *pdev)1050{1051 struct device *dev = &pdev->dev;1052 void __iomem *regs;1053 struct mhuv3 *mhu;1054 int ret;1055 1056 mhu = devm_kzalloc(dev, sizeof(*mhu), GFP_KERNEL);1057 if (!mhu)1058 return -ENOMEM;1059 1060 regs = devm_platform_ioremap_resource(pdev, 0);1061 if (IS_ERR(regs))1062 return PTR_ERR(regs);1063 1064 mhu->mbox.dev = dev;1065 ret = mhuv3_frame_init(mhu, regs);1066 if (ret)1067 return ret;1068 1069 ret = mhuv3_irqs_init(mhu, pdev);1070 if (ret)1071 return ret;1072 1073 mhu->mbox.of_xlate = mhuv3_mbox_of_xlate;1074 ret = mhuv3_initialize_channels(dev, mhu);1075 if (ret)1076 return ret;1077 1078 ret = devm_mbox_controller_register(dev, &mhu->mbox);1079 if (ret)1080 return dev_err_probe(dev, ret,1081 "Failed to register ARM MHUv3 driver\n");1082 1083 return ret;1084}1085 1086static const struct of_device_id mhuv3_of_match[] = {1087 { .compatible = "arm,mhuv3", .data = NULL },1088 {}1089};1090MODULE_DEVICE_TABLE(of, mhuv3_of_match);1091 1092static struct platform_driver mhuv3_driver = {1093 .driver = {1094 .name = "arm-mhuv3-mailbox",1095 .of_match_table = mhuv3_of_match,1096 },1097 .probe = mhuv3_probe,1098};1099module_platform_driver(mhuv3_driver);1100 1101MODULE_LICENSE("GPL");1102MODULE_DESCRIPTION("ARM MHUv3 Driver");1103MODULE_AUTHOR("Cristian Marussi <cristian.marussi@arm.com>");1104