Skip to content

Commit 7b972f3

Browse files
committed
Merge tag 'imx-drivers-5.8' of git://git.kernel.org/pub/scm/linux/kernel/git/shawnguo/linux into arm/drivers
i.MX drivers update for 5.8: - Optimize imx-scu driver to use one TX and one RX instead of four for talking to SCU. - Fix one possible message header corruption where the response is longer than the request. - Move System Control defines into dt-bindings header, so that DT can use them as well. - A couple of small fixups. * tag 'imx-drivers-5.8' of git://git.kernel.org/pub/scm/linux/kernel/git/shawnguo/linux: firmware: imx: scu: Fix possible memory leak in imx_scu_probe() dt-bindings: firmware: imx: Add more system controls and PM clock types dt-bindings: firmware: imx: Move system control into dt-binding headfile firmware: imx: scu: Fix corruption of header firmware: imx-scu: Support one TX and one RX soc: imx8m: No need to put node when of_find_compatible_node() failed Link: https://lore.kernel.org/r/[email protected] Signed-off-by: Arnd Bergmann <[email protected]>
2 parents e26552c + 89f12d6 commit 7b972f3

File tree

6 files changed

+136
-87
lines changed

6 files changed

+136
-87
lines changed

drivers/firmware/imx/imx-scu.c

Lines changed: 48 additions & 16 deletions
Original file line numberDiff line numberDiff line change
@@ -8,7 +8,6 @@
88
*/
99

1010
#include <linux/err.h>
11-
#include <linux/firmware/imx/types.h>
1211
#include <linux/firmware/imx/ipc.h>
1312
#include <linux/firmware/imx/sci.h>
1413
#include <linux/interrupt.h>
@@ -38,6 +37,7 @@ struct imx_sc_ipc {
3837
struct device *dev;
3938
struct mutex lock;
4039
struct completion done;
40+
bool fast_ipc;
4141

4242
/* temporarily store the SCU msg */
4343
u32 *msg;
@@ -115,13 +115,27 @@ static void imx_scu_rx_callback(struct mbox_client *c, void *msg)
115115
struct imx_sc_ipc *sc_ipc = sc_chan->sc_ipc;
116116
struct imx_sc_rpc_msg *hdr;
117117
u32 *data = msg;
118+
int i;
118119

119120
if (!sc_ipc->msg) {
120121
dev_warn(sc_ipc->dev, "unexpected rx idx %d 0x%08x, ignore!\n",
121122
sc_chan->idx, *data);
122123
return;
123124
}
124125

126+
if (sc_ipc->fast_ipc) {
127+
hdr = msg;
128+
sc_ipc->rx_size = hdr->size;
129+
sc_ipc->msg[0] = *data++;
130+
131+
for (i = 1; i < sc_ipc->rx_size; i++)
132+
sc_ipc->msg[i] = *data++;
133+
134+
complete(&sc_ipc->done);
135+
136+
return;
137+
}
138+
125139
if (sc_chan->idx == 0) {
126140
hdr = msg;
127141
sc_ipc->rx_size = hdr->size;
@@ -143,20 +157,22 @@ static void imx_scu_rx_callback(struct mbox_client *c, void *msg)
143157

144158
static int imx_scu_ipc_write(struct imx_sc_ipc *sc_ipc, void *msg)
145159
{
146-
struct imx_sc_rpc_msg *hdr = msg;
160+
struct imx_sc_rpc_msg hdr = *(struct imx_sc_rpc_msg *)msg;
147161
struct imx_sc_chan *sc_chan;
148162
u32 *data = msg;
149163
int ret;
164+
int size;
150165
int i;
151166

152167
/* Check size */
153-
if (hdr->size > IMX_SC_RPC_MAX_MSG)
168+
if (hdr.size > IMX_SC_RPC_MAX_MSG)
154169
return -EINVAL;
155170

156-
dev_dbg(sc_ipc->dev, "RPC SVC %u FUNC %u SIZE %u\n", hdr->svc,
157-
hdr->func, hdr->size);
171+
dev_dbg(sc_ipc->dev, "RPC SVC %u FUNC %u SIZE %u\n", hdr.svc,
172+
hdr.func, hdr.size);
158173

159-
for (i = 0; i < hdr->size; i++) {
174+
size = sc_ipc->fast_ipc ? 1 : hdr.size;
175+
for (i = 0; i < size; i++) {
160176
sc_chan = &sc_ipc->chans[i % 4];
161177

162178
/*
@@ -168,8 +184,10 @@ static int imx_scu_ipc_write(struct imx_sc_ipc *sc_ipc, void *msg)
168184
* Wait for tx_done before every send to ensure that no
169185
* queueing happens at the mailbox channel level.
170186
*/
171-
wait_for_completion(&sc_chan->tx_done);
172-
reinit_completion(&sc_chan->tx_done);
187+
if (!sc_ipc->fast_ipc) {
188+
wait_for_completion(&sc_chan->tx_done);
189+
reinit_completion(&sc_chan->tx_done);
190+
}
173191

174192
ret = mbox_send_message(sc_chan->ch, &data[i]);
175193
if (ret < 0)
@@ -246,18 +264,29 @@ static int imx_scu_probe(struct platform_device *pdev)
246264
struct imx_sc_chan *sc_chan;
247265
struct mbox_client *cl;
248266
char *chan_name;
267+
struct of_phandle_args args;
268+
int num_channel;
249269
int ret;
250270
int i;
251271

252272
sc_ipc = devm_kzalloc(dev, sizeof(*sc_ipc), GFP_KERNEL);
253273
if (!sc_ipc)
254274
return -ENOMEM;
255275

256-
for (i = 0; i < SCU_MU_CHAN_NUM; i++) {
257-
if (i < 4)
276+
ret = of_parse_phandle_with_args(pdev->dev.of_node, "mboxes",
277+
"#mbox-cells", 0, &args);
278+
if (ret)
279+
return ret;
280+
281+
sc_ipc->fast_ipc = of_device_is_compatible(args.np, "fsl,imx8-mu-scu");
282+
283+
num_channel = sc_ipc->fast_ipc ? 2 : SCU_MU_CHAN_NUM;
284+
for (i = 0; i < num_channel; i++) {
285+
if (i < num_channel / 2)
258286
chan_name = kasprintf(GFP_KERNEL, "tx%d", i);
259287
else
260-
chan_name = kasprintf(GFP_KERNEL, "rx%d", i - 4);
288+
chan_name = kasprintf(GFP_KERNEL, "rx%d",
289+
i - num_channel / 2);
261290

262291
if (!chan_name)
263292
return -ENOMEM;
@@ -269,19 +298,22 @@ static int imx_scu_probe(struct platform_device *pdev)
269298
cl->knows_txdone = true;
270299
cl->rx_callback = imx_scu_rx_callback;
271300

272-
/* Initial tx_done completion as "done" */
273-
cl->tx_done = imx_scu_tx_done;
274-
init_completion(&sc_chan->tx_done);
275-
complete(&sc_chan->tx_done);
301+
if (!sc_ipc->fast_ipc) {
302+
/* Initial tx_done completion as "done" */
303+
cl->tx_done = imx_scu_tx_done;
304+
init_completion(&sc_chan->tx_done);
305+
complete(&sc_chan->tx_done);
306+
}
276307

277308
sc_chan->sc_ipc = sc_ipc;
278-
sc_chan->idx = i % 4;
309+
sc_chan->idx = i % (num_channel / 2);
279310
sc_chan->ch = mbox_request_channel_byname(cl, chan_name);
280311
if (IS_ERR(sc_chan->ch)) {
281312
ret = PTR_ERR(sc_chan->ch);
282313
if (ret != -EPROBE_DEFER)
283314
dev_err(dev, "Failed to request mbox chan %s ret %d\n",
284315
chan_name, ret);
316+
kfree(chan_name);
285317
return ret;
286318
}
287319

drivers/soc/imx/soc-imx8m.c

Lines changed: 3 additions & 4 deletions
Original file line numberDiff line numberDiff line change
@@ -53,11 +53,11 @@ static u32 __init imx8mq_soc_revision(void)
5353
struct device_node *np;
5454
void __iomem *ocotp_base;
5555
u32 magic;
56-
u32 rev = 0;
56+
u32 rev;
5757

5858
np = of_find_compatible_node(NULL, NULL, "fsl,imx8mq-ocotp");
5959
if (!np)
60-
goto out;
60+
return 0;
6161

6262
ocotp_base = of_iomap(np, 0);
6363
WARN_ON(!ocotp_base);
@@ -78,9 +78,8 @@ static u32 __init imx8mq_soc_revision(void)
7878
soc_uid |= readl_relaxed(ocotp_base + OCOTP_UID_LOW);
7979

8080
iounmap(ocotp_base);
81-
82-
out:
8381
of_node_put(np);
82+
8483
return rev;
8584
}
8685

drivers/thermal/imx_sc_thermal.c

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -3,9 +3,9 @@
33
* Copyright 2018-2020 NXP.
44
*/
55

6+
#include <dt-bindings/firmware/imx/rsrc.h>
67
#include <linux/err.h>
78
#include <linux/firmware/imx/sci.h>
8-
#include <linux/firmware/imx/types.h>
99
#include <linux/module.h>
1010
#include <linux/of.h>
1111
#include <linux/of_device.h>

include/dt-bindings/firmware/imx/rsrc.h

Lines changed: 84 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -547,4 +547,88 @@
547547
#define IMX_SC_R_ATTESTATION 545
548548
#define IMX_SC_R_LAST 546
549549

550+
/*
551+
* Defines for SC PM CLK
552+
*/
553+
#define IMX_SC_PM_CLK_SLV_BUS 0 /* Slave bus clock */
554+
#define IMX_SC_PM_CLK_MST_BUS 1 /* Master bus clock */
555+
#define IMX_SC_PM_CLK_PER 2 /* Peripheral clock */
556+
#define IMX_SC_PM_CLK_PHY 3 /* Phy clock */
557+
#define IMX_SC_PM_CLK_MISC 4 /* Misc clock */
558+
#define IMX_SC_PM_CLK_MISC0 0 /* Misc 0 clock */
559+
#define IMX_SC_PM_CLK_MISC1 1 /* Misc 1 clock */
560+
#define IMX_SC_PM_CLK_MISC2 2 /* Misc 2 clock */
561+
#define IMX_SC_PM_CLK_MISC3 3 /* Misc 3 clock */
562+
#define IMX_SC_PM_CLK_MISC4 4 /* Misc 4 clock */
563+
#define IMX_SC_PM_CLK_CPU 2 /* CPU clock */
564+
#define IMX_SC_PM_CLK_PLL 4 /* PLL */
565+
#define IMX_SC_PM_CLK_BYPASS 4 /* Bypass clock */
566+
567+
/*
568+
* Defines for SC CONTROL
569+
*/
570+
#define IMX_SC_C_TEMP 0
571+
#define IMX_SC_C_TEMP_HI 1
572+
#define IMX_SC_C_TEMP_LOW 2
573+
#define IMX_SC_C_PXL_LINK_MST1_ADDR 3
574+
#define IMX_SC_C_PXL_LINK_MST2_ADDR 4
575+
#define IMX_SC_C_PXL_LINK_MST_ENB 5
576+
#define IMX_SC_C_PXL_LINK_MST1_ENB 6
577+
#define IMX_SC_C_PXL_LINK_MST2_ENB 7
578+
#define IMX_SC_C_PXL_LINK_SLV1_ADDR 8
579+
#define IMX_SC_C_PXL_LINK_SLV2_ADDR 9
580+
#define IMX_SC_C_PXL_LINK_MST_VLD 10
581+
#define IMX_SC_C_PXL_LINK_MST1_VLD 11
582+
#define IMX_SC_C_PXL_LINK_MST2_VLD 12
583+
#define IMX_SC_C_SINGLE_MODE 13
584+
#define IMX_SC_C_ID 14
585+
#define IMX_SC_C_PXL_CLK_POLARITY 15
586+
#define IMX_SC_C_LINESTATE 16
587+
#define IMX_SC_C_PCIE_G_RST 17
588+
#define IMX_SC_C_PCIE_BUTTON_RST 18
589+
#define IMX_SC_C_PCIE_PERST 19
590+
#define IMX_SC_C_PHY_RESET 20
591+
#define IMX_SC_C_PXL_LINK_RATE_CORRECTION 21
592+
#define IMX_SC_C_PANIC 22
593+
#define IMX_SC_C_PRIORITY_GROUP 23
594+
#define IMX_SC_C_TXCLK 24
595+
#define IMX_SC_C_CLKDIV 25
596+
#define IMX_SC_C_DISABLE_50 26
597+
#define IMX_SC_C_DISABLE_125 27
598+
#define IMX_SC_C_SEL_125 28
599+
#define IMX_SC_C_MODE 29
600+
#define IMX_SC_C_SYNC_CTRL0 30
601+
#define IMX_SC_C_KACHUNK_CNT 31
602+
#define IMX_SC_C_KACHUNK_SEL 32
603+
#define IMX_SC_C_SYNC_CTRL1 33
604+
#define IMX_SC_C_DPI_RESET 34
605+
#define IMX_SC_C_MIPI_RESET 35
606+
#define IMX_SC_C_DUAL_MODE 36
607+
#define IMX_SC_C_VOLTAGE 37
608+
#define IMX_SC_C_PXL_LINK_SEL 38
609+
#define IMX_SC_C_OFS_SEL 39
610+
#define IMX_SC_C_OFS_AUDIO 40
611+
#define IMX_SC_C_OFS_PERIPH 41
612+
#define IMX_SC_C_OFS_IRQ 42
613+
#define IMX_SC_C_RST0 43
614+
#define IMX_SC_C_RST1 44
615+
#define IMX_SC_C_SEL0 45
616+
#define IMX_SC_C_CALIB0 46
617+
#define IMX_SC_C_CALIB1 47
618+
#define IMX_SC_C_CALIB2 48
619+
#define IMX_SC_C_IPG_DEBUG 49
620+
#define IMX_SC_C_IPG_DOZE 50
621+
#define IMX_SC_C_IPG_WAIT 51
622+
#define IMX_SC_C_IPG_STOP 52
623+
#define IMX_SC_C_IPG_STOP_MODE 53
624+
#define IMX_SC_C_IPG_STOP_ACK 54
625+
#define IMX_SC_C_SYNC_CTRL 55
626+
#define IMX_SC_C_OFS_AUDIO_ALT 56
627+
#define IMX_SC_C_DSP_BYP 57
628+
#define IMX_SC_C_CLK_GEN_EN 58
629+
#define IMX_SC_C_INTF_SEL 59
630+
#define IMX_SC_C_RXC_DLY 60
631+
#define IMX_SC_C_TIMER_SEL 61
632+
#define IMX_SC_C_LAST 62
633+
550634
#endif /* __DT_BINDINGS_RSCRC_IMX_H */

include/linux/firmware/imx/sci.h

Lines changed: 0 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -11,7 +11,6 @@
1111
#define _SC_SCI_H
1212

1313
#include <linux/firmware/imx/ipc.h>
14-
#include <linux/firmware/imx/types.h>
1514

1615
#include <linux/firmware/imx/svc/misc.h>
1716
#include <linux/firmware/imx/svc/pm.h>

include/linux/firmware/imx/types.h

Lines changed: 0 additions & 65 deletions
This file was deleted.

0 commit comments

Comments
 (0)