Release develop 251028

This commit is contained in:
hongyi
2025-10-28 14:02:38 +08:00
parent 28b59bd5a6
commit 57e0342c1f
10 changed files with 444 additions and 126 deletions

View File

@@ -277,6 +277,17 @@
slew-rate = <0>;
};
};
pwm0_pins: pwm0-1 {
pwm0-pins {
pins = "GPIO0_30"; // PWM0_CH2
function = "pwm0";
bias-disable;
drive-strength = <13>;
input-disable;
input-schmitt-disable;
slew-rate = <0>;
};
};
gmac1_pins: gmac1-0 {
txclk-pins {
pins = "GPIO1_2", /* GMAC1_TX_CLK */
@@ -438,17 +449,6 @@
slew-rate = <0>;
};
};
pwm0_pins: pwm0-1 {
pwm0-pins {
pins = "GPIO0_30"; // PWM0_CH2
function = "pwm0";
bias-disable;
drive-strength = <13>;
input-disable;
input-schmitt-disable;
slew-rate = <0>;
};
};
pwm1_pins: pwm1-1 {
pwm1-pins {
pins = "GPIO2_12"; // PWM1_CH2

View File

@@ -19,6 +19,12 @@
numa-node-id = <0>;
};
memory@2080000000 {
device_type = "memory";
reg = <0x20 0x80000000 0x02 0x00000000>; // 8G
numa-node-id = <1>;
};
reserved-memory {
#address-cells = <2>;
#size-cells = <2>;
@@ -64,70 +70,6 @@
};
};
&reset {
control-val = <0x3 0x0 0x3 0x0>;
};
&c908_1 {
status = "disable";
};
&c908_2 {
status = "disable";
};
&c908_3 {
status = "disable";
};
&c920_4 {
status = "disable";
};
&c920_5 {
status = "disable";
};
&c920_6 {
status = "disable";
};
&c920_7 {
status = "disable";
};
&c908_8 {
//status = "disable";
};
&c908_9 {
status = "disable";
};
&c908_10 {
status = "disable";
};
&c908_11 {
status = "disable";
};
&c920_12 {
status = "disable";
};
&c920_13 {
status = "disable";
};
&c920_14 {
status = "disable";
};
&c920_15 {
status = "disable";
};
&uart0 {
status = "disabled";
};

View File

@@ -1623,6 +1623,7 @@
interrupts = <336 IRQ_TYPE_LEVEL_HIGH>;
icu_cpu_id = <0>;
#mbox-cells = <2>;
version = <1>;
status = "okay";
};
aon: aon_subsys {
@@ -1630,6 +1631,7 @@
mbox-names = "aon0";
mboxes = <&mbox_920 1 0>; //parent / channel / type
#mbox-cells = <2>;
version = <1>;
status = "okay";
};

View File

@@ -87,6 +87,7 @@ CONFIG_PCI=y
CONFIG_PCIE_ZH=m
CONFIG_DEVTMPFS=y
CONFIG_DEVTMPFS_MOUNT=y
CONFIG_ZHIHE_PROC_DEBUG=y
CONFIG_MTD=y
CONFIG_MTD_OF_PARTS=m
CONFIG_MTD_BLOCK=y

View File

@@ -10,3 +10,7 @@ config ZHIHE_AON
This driver manages the IPC interface between host cpu liks thead
and the Aon firmware running on thead riscv E902 core.
config ZHIHE_PROC_DEBUG
bool "ZHIHE debug"
help
proc_debug

View File

@@ -1,2 +1,3 @@
# SPDX-License-Identifier: GPL-2.0
obj-$(CONFIG_ZHIHE_AON) += zhihe_aon.o
obj-$(CONFIG_ZHIHE_AON) += zhihe_aon.o
obj-$(CONFIG_ZHIHE_PROC_DEBUG) += zhihe_proc_debug.o

View File

@@ -16,6 +16,10 @@
#include <linux/of_device.h>
#include <linux/platform_device.h>
#include <linux/proc_fs.h>
#include <linux/zhihe_proc_debug.h>
#define ZHIHE_AON_V1 0x0
#define ZHIHE_AON_V2 0x1
/* wait for response for 3000ms instead of 300ms (fix me pls)*/
#define MAX_RX_TIMEOUT (msecs_to_jiffies(3000))
@@ -207,6 +211,32 @@ out:
}
EXPORT_SYMBOL(zhihe_aon_call_rpc);
int get_aon_log_mem(struct device *dev, phys_addr_t *mem, size_t *mem_size)
{
struct resource r;
struct device_node *node;
int ret;
*mem = 0;
*mem_size = 0;
node = of_parse_phandle(dev->of_node, "log-memory-region", 0);
if (!node) {
dev_err(dev, "no memory-region specified\n");
return -EINVAL;
}
ret = of_address_to_resource(node, 0, &r);
if (ret) {
dev_err(dev, "memory-region get resource faild\n");
return -EINVAL;
}
*mem = r.start;
*mem_size = resource_size(&r);
return 0;
}
static int zhihe_aon_probe(struct platform_device *pdev)
{
struct device *dev = &pdev->dev;
@@ -214,6 +244,7 @@ static int zhihe_aon_probe(struct platform_device *pdev)
struct zhihe_aon_chan *aon_chan;
struct mbox_client *cl;
struct device_node *np;
char dir_name[32] = { 0x0 };
int ret;
aon_ipc = devm_kzalloc(dev, sizeof(*aon_ipc), GFP_KERNEL);
if (!aon_ipc)
@@ -251,6 +282,28 @@ static int zhihe_aon_probe(struct platform_device *pdev)
dev_err(dev, "aon_ipc:%s handle num overflow\n",aon_ipc->mbox_name);
return -1;
}
ret = get_aon_log_mem(dev, &aon_chan->log_phy, &aon_chan->log_size);
if (!ret) {
aon_chan->log_mem = ioremap(aon_chan->log_phy, aon_chan->log_size);
if (IS_ERR(aon_chan->log_mem)) {
aon_chan->log_mem = NULL;
dev_err(dev, "%s:get aon log region fail\n", __func__);
return -1;
}
sprintf(dir_name, "aon_proc");
aon_chan->proc_dir = proc_mkdir(dir_name, NULL);
if (NULL != aon_chan->proc_dir) {
aon_chan->log_ctrl = zhihe_create_panic_log_proc(
aon_chan->log_phy, aon_chan->proc_dir,
aon_chan->log_mem, aon_chan->log_size);
} else {
dev_err(dev, "create %s fail\n", dir_name);
return ret;
}
}
zhihe_aon_ipc_handle[g_aon_ipc_handle_num] = aon_ipc;
g_aon_ipc_handle_num++;
return devm_of_platform_populate(dev);
@@ -291,3 +344,4 @@ MODULE_AUTHOR("hongkun.xu <xuhongkun@zhcomputing.com>");
MODULE_AUTHOR("xionglue.huang <huangxionglue@zhcomputing.com>");
MODULE_DESCRIPTION("ZHIHE firmware protocol driver");
MODULE_LICENSE("GPL v2");

View File

@@ -0,0 +1,163 @@
// SPDX-License-Identifier: GPL-2.0+
/*
* sys log sys for zhihe c908 and e902
* Copyright (C) 2021 ZHIHE Group Holding Limited.
*/
#include <linux/delay.h>
#include <linux/interrupt.h>
#include <linux/module.h>
#include <linux/of.h>
#include <linux/of_address.h>
#include <linux/of_device.h>
#include <linux/platform_device.h>
#include <linux/proc_fs.h>
#include <linux/seq_file.h>
#include <linux/slab.h>
#include <linux/io.h>
#include <asm/cacheflush.h>
#define GET_PAGE_NUM(size, offset) \
((((size) + ((offset) & ~PAGE_MASK)) + PAGE_SIZE - 1) >> PAGE_SHIFT)
struct zhihe_log_ring_buffer {
__u32 read;
__u32 write;
__u32 size;
__u32 reserved[1];
__u8 data[0];
};
struct zhihe_hw_log {
__u32 panic;
__u32 reserved[2];
struct zhihe_log_ring_buffer rb;
};
struct zhihe_proc_log_ctrl {
struct zhihe_hw_log __iomem *log;
struct proc_dir_entry *log_proc_file;
phys_addr_t log_phy;
};
static void dump_regs(const char *fn, void *hw_arg)
{
struct zhihe_proc_log_ctrl *log_ctrl = hw_arg;
if (!log_ctrl->log)
return;
pr_debug("%s: panic = 0x%08x\n", fn,
__raw_readl(&log_ctrl->log->panic));
pr_debug("%s: read = 0x%08x, write = 0x%08x, size = 0x%08x\n", fn,
__raw_readl(&log_ctrl->log->rb.read),
__raw_readl(&log_ctrl->log->rb.write),
__raw_readl(&log_ctrl->log->rb.size));
}
static int log_proc_show(struct seq_file *file, void *v)
{
struct zhihe_proc_log_ctrl *log_ctrl = file->private;
char *buf;
size_t i;
/*dcache clean and invalid*/
ALT_CMO_OP(flush, (phys_to_virt(log_ctrl->log_phy)),
sizeof(struct zhihe_hw_log),
riscv_cbom_block_size);
uint32_t write = __raw_readl(&log_ctrl->log->rb.write);
uint32_t read = __raw_readl(&log_ctrl->log->rb.read);
uint32_t size = __raw_readl(&log_ctrl->log->rb.size);
size_t log_size = write >= read ? write - read : size + write - read;
seq_printf(file, "****************** device log >>>>>>>>>>>>>>>>>\n");
dump_regs(__func__, log_ctrl);
if (!log_size) {
seq_printf(file, "****************** end device log <<<<<<<<<<<<<<<<<\n");
return 0;
}
int page_num = GET_PAGE_NUM(log_size, 0);
int log_patch_1 = -1, log_patch_2 = -1;
buf = kmalloc(PAGE_SIZE * page_num, GFP_KERNEL);
if (buf) {
if (read + log_size >= size) {
log_patch_2 = read + log_size - size + 1;
log_patch_1 = log_size - log_patch_2;
} else
log_patch_1 = log_size;
memcpy_fromio(buf, &log_ctrl->log->rb.data[read], log_patch_1);
if (log_patch_2 > 0)
memcpy_fromio(buf, &log_ctrl->log->rb.data[0], log_patch_2);
uint8_t last_fame_size = log_size % 64;
for (i = 0; i < log_size - last_fame_size; i += 64)
seq_printf(file, " %*pEp", 64, buf + i);
if (last_fame_size)
seq_printf(file, " %*pEp", last_fame_size, buf + log_size - last_fame_size);
__raw_writel(write, &log_ctrl->log->rb.read);
kfree(buf);
/*dcahce clean*/
ALT_CMO_OP(clean, (phys_to_virt(log_ctrl->log_phy)),
sizeof(struct zhihe_hw_log), riscv_cbom_block_size);
//seq_printf(file,"\n%d %d %d %d %d\n",log_patch_1, log_patch_2, log_size ,last_fame_size, read);
seq_printf(file, "\n****************** end device log <<<<<<<<<<<<<<<<<\n");
return 0;
} else {
pr_debug("Fail to alloc buf\n");
return -1;
}
return 0;
}
static bool zhihe_panic_init(struct zhihe_hw_log *hw_log, size_t size)
{
if (size < sizeof(struct zhihe_hw_log))
return false;
hw_log->rb.read = 0;
hw_log->rb.size = size - sizeof(struct zhihe_hw_log);
return true;
}
void *zhihe_create_panic_log_proc(phys_addr_t log_phy, void *dir,
void *log_info_addr, size_t size)
{
struct zhihe_proc_log_ctrl *log_ctrl =
kmalloc(sizeof(struct zhihe_proc_log_ctrl), GFP_KERNEL);
if (log_ctrl == NULL)
return NULL;
log_ctrl->log = log_info_addr;
zhihe_panic_init(log_ctrl->log, size);
log_ctrl->log_proc_file = proc_create_single_data(
"proc_log", 0644, dir, &log_proc_show, log_ctrl);
if (log_ctrl->log_proc_file == NULL) {
pr_debug("Error: Could not initialize %s\n", "dsp_log");
kfree(log_ctrl);
log_ctrl = NULL;
} else
pr_debug("%s create Success!\n", "dsp_log");
log_ctrl->log_phy = log_phy;
return log_ctrl;
}
void zhihe_remove_panic_log_proc(void *arg)
{
struct zhihe_proc_log_ctrl *log_ctrl = (struct zhihe_proc_log_ctrl *)arg;
proc_remove(log_ctrl->log_proc_file);
kfree(log_ctrl);
pr_debug("zhihe proc log removed\n");
}

View File

@@ -17,6 +17,9 @@
#include <linux/of_device.h>
#include <linux/slab.h>
#define ZHIHE_MBOX_V1 0x0
#define ZHIHE_MBOX_V2 0x1
/* Status Register */
#define ZHIHE_MBOX_STA 0x0
#define ZHIHE_MBOX_CLR 0x4
@@ -53,27 +56,29 @@ enum zhihe_mbox_chan_type {
ZHIHE_MBOX_TYPE_TXRX, /* Tx & Rx chan */
ZHIHE_MBOX_TYPE_DB, /* Tx & Rx doorbell */
};
enum zhihe_mbox_icu_cpu_id {
ZHIHE_MBOX_ICU_CPU0 = 0, /*die0-908*/
ZHIHE_MBOX_ICU_CPU1 = 1,
ZHIHE_MBOX_ICU_CPU2 = 2,
ZHIHE_MBOX_ICU_CPU3 = 3,
ZHIHE_MBOX_ICU_CPU0 = 0, /* A200:910T,A210:die0-908 */
ZHIHE_MBOX_ICU_CPU1 = 1, /* A200:902 */
ZHIHE_MBOX_ICU_CPU2 = 2, /* A200:906 */
ZHIHE_MBOX_ICU_CPU3 = 3, /* A200:910R */
};
enum zhihe_mbox_local_id {
ZHIHE_MBOX_INTERRUPT = 0,
ZHIHE_MBOX_DATA_CH0 = 1, /* die0-908--die0-902*/
ZHIHE_MBOX_DATA_CH0 = 1, /* A210:die0-908--die0-902 */
ZHIHE_MBOX_DATA_CH1 = 2,
ZHIHE_MBOX_DATA_CH2 = 3,
};
enum zhihe_mbox_remote_id {
ZHIHE_MBOX_REMOTE_CH0 = 0, /* die0-908--die0-902*/
ZHIHE_MBOX_REMOTE_CH0 = 0, /* A210:die0-908--die0-902 */
ZHIHE_MBOX_REMOTE_CH1 = 1,
ZHIHE_MBOX_REMOTE_CH2 = 2,
};
struct zhihe_mbox_con_priv {
enum zhihe_mbox_local_id idx;
enum zhihe_mbox_icu_cpu_id icu_cpu_idx;
enum zhihe_mbox_local_id local_idx;
enum zhihe_mbox_chan_type type;
void __iomem *comm_local_base;
void __iomem *comm_remote_base;
@@ -96,6 +101,7 @@ struct zhihe_mbox_priv {
struct zhihe_mbox_con_priv con_priv[ZHIHE_MBOX_CHANS];
struct clk *clk;
int irq;
int version;
#ifdef CONFIG_PM_SLEEP
struct zhihe_mbox_context *ctx;
#endif
@@ -144,12 +150,10 @@ static void zhihe_mbox_chan_write(struct zhihe_mbox_con_priv *cp,
static u32 zhihe_mbox_chan_read(struct zhihe_mbox_con_priv *cp,
u32 offs, bool is_remote)
{
uint32_t t = 0;
if (is_remote)
t = ioread32(cp->comm_remote_base + offs);
return ioread32(cp->comm_remote_base + offs);
else
t = ioread32(cp->comm_local_base + offs);
return t;
return ioread32(cp->comm_local_base + offs);
}
static void zhihe_mbox_chan_rmw(struct zhihe_mbox_con_priv *cp,
@@ -213,12 +217,26 @@ static int zhihe_mbox_chan_id_to_mapbit(struct zhihe_mbox_con_priv *cp)
{
int i;
int mapbit = 0;
for (i = 0; i < ZHIHE_MBOX_CHANS; i++) {
if (i == cp->idx)
return mapbit;
struct zhihe_mbox_priv *priv = to_zhihe_mbox_priv(cp->chan->mbox);
if (i != ZHIHE_MBOX_INTERRUPT)
mapbit++;
if (priv->version == ZHIHE_MBOX_V1) {
for (i = 0; i < ZHIHE_MBOX_CHANS; i++) {
if (i == cp->icu_cpu_idx)
return mapbit;
if (i != priv->cur_icu_cpu_id)
mapbit++;
}
} else if (priv->version == ZHIHE_MBOX_V2) {
for (i = 0; i < ZHIHE_MBOX_CHANS; i++) {
if (i == cp->local_idx)
return mapbit;
if (i != ZHIHE_MBOX_INTERRUPT)
mapbit++;
}
} else {
dev_err(cp->chan->mbox->dev, "Unknown zhihe mailbox version\n");
}
if (i == ZHIHE_MBOX_CHANS)
@@ -264,6 +282,14 @@ static irqreturn_t zhihe_mbox_isr(int irq, void *p)
zhihe_mbox_chan_write(cp, 0x0, ZHIHE_MBOX_INFO0, false);
/* notify remote cpu */
zhihe_mbox_chan_wr_ack(cp, &ack_magic, true);
if (priv->version == ZHIHE_MBOX_V1) {
/* CPU1 902/906 use polling mode to monitor info7 */
if (cp->icu_cpu_idx != ZHIHE_MBOX_ICU_CPU1 &&
cp->icu_cpu_idx != ZHIHE_MBOX_ICU_CPU2)
zhihe_mbox_chan_rmw(cp, ZHIHE_MBOX_GEN,
ZHIHE_MBOX_GEN_TX_ACK, 0, true);
}
/* transfer the data to client */
mbox_chan_received_data(chan, (void *)dat);
}
@@ -362,6 +388,7 @@ static struct mbox_chan *zhihe_mbox_xlate(struct mbox_controller *mbox,
{
u32 chan, type;
struct zhihe_mbox_con_priv *cp;
struct zhihe_mbox_priv *priv = to_zhihe_mbox_priv(mbox);
if (sp->args_count != 2) {
dev_err(mbox->dev,
@@ -376,6 +403,13 @@ static struct mbox_chan *zhihe_mbox_xlate(struct mbox_controller *mbox,
return ERR_PTR(-EINVAL);
}
if (priv->version == ZHIHE_MBOX_V1) {
if (chan == priv->cur_icu_cpu_id) {
dev_err(mbox->dev, "Cannot communicate with yourself\n");
return ERR_PTR(-EINVAL);
}
}
if (type > ZHIHE_MBOX_TYPE_DB) {
dev_err(mbox->dev,
"Not supported the type for channel[%d]\n", chan);
@@ -392,6 +426,7 @@ static int zhihe_mbox_probe(struct platform_device *pdev)
{
int ret;
unsigned int i;
unsigned int mbox_id;
struct resource *res;
struct zhihe_mbox_priv *priv;
unsigned int remote_idx = 0;
@@ -402,40 +437,124 @@ static int zhihe_mbox_probe(struct platform_device *pdev)
if (!priv)
return -ENOMEM;
ret = of_property_read_u32(np, "version", &priv->version);
if (ret) {
priv->version = ZHIHE_MBOX_V1;
}
if (of_property_read_u32(np, "icu_cpu_id", &priv->cur_icu_cpu_id)) {
dev_err(dev, "icu_cpu_id is missing\n");
return -EINVAL;
}
if (priv->version == ZHIHE_MBOX_V1) {
if (priv->cur_icu_cpu_id != ZHIHE_MBOX_ICU_CPU0 &&
priv->cur_icu_cpu_id != ZHIHE_MBOX_ICU_CPU3) {
dev_err(dev, "icu_cpu_id is invalid\n");
return -EINVAL;
}
}
priv->dev = dev;
res = platform_get_resource_byname(pdev, IORESOURCE_MEM, "interrupt_addr");
priv->local_icu[ZHIHE_MBOX_INTERRUPT] = devm_ioremap_resource(dev, res);
if (IS_ERR(priv->local_icu[ZHIHE_MBOX_INTERRUPT]))
return PTR_ERR(priv->local_icu[ZHIHE_MBOX_INTERRUPT]);
res = platform_get_resource_byname(pdev, IORESOURCE_MEM, "local_addr0");
priv->local_icu[ZHIHE_MBOX_DATA_CH0] = devm_ioremap_resource(dev, res);
if (IS_ERR(priv->local_icu[ZHIHE_MBOX_DATA_CH0]))
return PTR_ERR(priv->local_icu[ZHIHE_MBOX_DATA_CH0]);
res = platform_get_resource_byname(pdev, IORESOURCE_MEM, "remote_icu0");
priv->remote_icu[ZHIHE_MBOX_REMOTE_CH0] = devm_ioremap_resource(dev, res);
if (IS_ERR(priv->remote_icu[ZHIHE_MBOX_REMOTE_CH0]))
return PTR_ERR(priv->remote_icu[ZHIHE_MBOX_REMOTE_CH0]);
res = platform_get_resource_byname(pdev, IORESOURCE_MEM, "local_addr1");
res = platform_get_resource_byname(pdev, IORESOURCE_MEM, "local_addr0");
if(res!=NULL) {
priv->local_icu[ZHIHE_MBOX_DATA_CH1] = devm_ioremap_resource(dev, res);
if (IS_ERR(priv->local_icu[ZHIHE_MBOX_DATA_CH1]))
return PTR_ERR(priv->local_icu[ZHIHE_MBOX_DATA_CH1]);
if (priv->version == ZHIHE_MBOX_V1) {
mbox_id = ZHIHE_MBOX_ICU_CPU0;
} else if (priv->version == ZHIHE_MBOX_V2) {
mbox_id = ZHIHE_MBOX_DATA_CH0;
} else {
dev_err(dev, "Unknown zhihe mailbox version\n");
}
priv->local_icu[mbox_id] = devm_ioremap_resource(dev, res);
if (IS_ERR(priv->local_icu[mbox_id]))
return PTR_ERR(priv->local_icu[mbox_id]);
} else {
dev_err(dev, "local_addr0 is NULL\n");
}
if (priv->version == ZHIHE_MBOX_V2) {
res = platform_get_resource_byname(pdev, IORESOURCE_MEM, "local_addr1");
if(res!=NULL) {
mbox_id = ZHIHE_MBOX_DATA_CH1;
priv->local_icu[mbox_id] = devm_ioremap_resource(dev, res);
if (IS_ERR(priv->local_icu[mbox_id]))
return PTR_ERR(priv->local_icu[mbox_id]);
} else {
dev_err(dev, "local_addr1 is NULL\n");
}
res = platform_get_resource_byname(pdev, IORESOURCE_MEM, "interrupt_addr");
if(res!=NULL) {
mbox_id = ZHIHE_MBOX_INTERRUPT;
priv->local_icu[mbox_id] = devm_ioremap_resource(dev, res);
if (IS_ERR(priv->local_icu[mbox_id]))
return PTR_ERR(priv->local_icu[mbox_id]);
} else {
dev_err(dev, "interrupt_addr is NULL\n");
}
}
res = platform_get_resource_byname(pdev, IORESOURCE_MEM, "remote_icu0");
if(res!=NULL) {
if (priv->version == ZHIHE_MBOX_V1) {
mbox_id = 0;
} else if (priv->version == ZHIHE_MBOX_V2) {
mbox_id = ZHIHE_MBOX_REMOTE_CH0;
} else {
dev_err(dev, "Unknown zhihe mailbox version\n");
}
priv->remote_icu[mbox_id] = devm_ioremap_resource(dev, res);
if (IS_ERR(priv->remote_icu[mbox_id]))
return PTR_ERR(priv->remote_icu[mbox_id]);
} else {
dev_err(dev, "remote_icu0 is NULL\n");
}
res = platform_get_resource_byname(pdev, IORESOURCE_MEM, "remote_icu1");
if(res!=NULL) {
priv->remote_icu[ZHIHE_MBOX_REMOTE_CH1] = devm_ioremap_resource(dev, res);
if (IS_ERR(priv->remote_icu[ZHIHE_MBOX_REMOTE_CH1]))
return PTR_ERR(priv->remote_icu[ZHIHE_MBOX_REMOTE_CH1]);
if (priv->version == ZHIHE_MBOX_V1) {
mbox_id = 1;
} else if (priv->version == ZHIHE_MBOX_V2) {
mbox_id = ZHIHE_MBOX_REMOTE_CH1;
} else {
dev_err(dev, "Unknown zhihe mailbox version\n");
}
priv->remote_icu[mbox_id] = devm_ioremap_resource(dev, res);
if (IS_ERR(priv->remote_icu[mbox_id]))
return PTR_ERR(priv->remote_icu[mbox_id]);
} else {
dev_err(dev, "remote_icu1 is NULL\n");
}
priv->cur_cpu_ch_base = priv->local_icu[ZHIHE_MBOX_INTERRUPT];
if (priv->version == ZHIHE_MBOX_V1) {
res = platform_get_resource_byname(pdev, IORESOURCE_MEM, "remote_icu2");
if(res!=NULL) {
mbox_id = 2;
priv->remote_icu[mbox_id] = devm_ioremap_resource(dev, res);
if (IS_ERR(priv->remote_icu[mbox_id]))
return PTR_ERR(priv->remote_icu[mbox_id]);
} else {
dev_err(dev, "remote_icu2 is NULL\n");
}
priv->local_icu[ZHIHE_MBOX_ICU_CPU1] =
priv->local_icu[ZHIHE_MBOX_ICU_CPU0] +
ZHIHE_MBOX_CHAN_RES_SIZE;
priv->local_icu[ZHIHE_MBOX_ICU_CPU2] =
priv->local_icu[ZHIHE_MBOX_ICU_CPU1] +
ZHIHE_MBOX_CHAN_RES_SIZE;
priv->local_icu[ZHIHE_MBOX_ICU_CPU3] =
priv->local_icu[ZHIHE_MBOX_ICU_CPU2] +
ZHIHE_MBOX_CHAN_RES_SIZE;
mbox_id = priv->cur_icu_cpu_id;
}else {
mbox_id = ZHIHE_MBOX_INTERRUPT;
}
priv->cur_cpu_ch_base = priv->local_icu[mbox_id];
priv->irq = platform_get_irq(pdev, 0);
if (priv->irq < 0)
return priv->irq;
@@ -451,19 +570,38 @@ static int zhihe_mbox_probe(struct platform_device *pdev)
return ret;
}
/* init the chans */
for (i = 0; i < ZHIHE_MBOX_CHANS; i++) {
struct zhihe_mbox_con_priv *cp = &priv->con_priv[i];
cp->idx = i;
cp->chan = &priv->mbox_chans[i];
priv->mbox_chans[i].con_priv = cp;
snprintf(cp->irq_desc, sizeof(cp->irq_desc),
"zhihe_mbox_chan[%i]", cp->idx);
cp->comm_local_base = priv->local_icu[i];
if (i != ZHIHE_MBOX_INTERRUPT) {
cp->comm_remote_base = priv->remote_icu[remote_idx];
remote_idx++;
if (priv->version == ZHIHE_MBOX_V1) {
for (i = 0; i < ZHIHE_MBOX_CHANS; i++) {
struct zhihe_mbox_con_priv *cp = &priv->con_priv[i];
cp->icu_cpu_idx = i;
cp->chan = &priv->mbox_chans[i];
priv->mbox_chans[i].con_priv = cp;
snprintf(cp->irq_desc, sizeof(cp->irq_desc),
"zhihe_mbox_chan[%i]", cp->icu_cpu_idx);
cp->comm_local_base = priv->local_icu[i];
if (i != priv->cur_icu_cpu_id) {
cp->comm_remote_base = priv->remote_icu[remote_idx];
remote_idx++;
}
}
} else if (priv->version == ZHIHE_MBOX_V2) {
for (i = 0; i < ZHIHE_MBOX_CHANS; i++) {
struct zhihe_mbox_con_priv *cp = &priv->con_priv[i];
cp->local_idx = i;
cp->chan = &priv->mbox_chans[i];
priv->mbox_chans[i].con_priv = cp;
snprintf(cp->irq_desc, sizeof(cp->irq_desc),
"zhihe_mbox_chan[%i]", cp->local_idx);
cp->comm_local_base = priv->local_icu[i];
if (i != ZHIHE_MBOX_INTERRUPT) {
cp->comm_remote_base = priv->remote_icu[remote_idx];
remote_idx++;
}
}
} else {
dev_err(dev, "Unknown zhihe mailbox version\n");
}
spin_lock_init(&priv->mbox_lock);
priv->mbox.dev = dev;

View File

@@ -0,0 +1,13 @@
// SPDX-License-Identifier: GPL-2.0+
/*
* Copyright (C) 2021 ZHIHE Group Holding Limited.
*/
#ifndef __ZHIHE_PROC_DEBUG_H_
#define __ZHIHE_PROC_DEBUG_H_
void *zhihe_create_panic_log_proc(phys_addr_t log_phy, void *dir, void *log_addr, size_t size);
void zhihe_remove_panic_log_proc(void *arg);
#endif