mirror of
https://github.com/hardkernel/linux.git
synced 2026-06-06 10:58:48 +09:00
media: rockchip: avsp: init driver for rv1126b
Change-Id: Idc461ba83d04b056249f025ca27bfbbd7fa4abbb Signed-off-by: Zhizhen Zheng <zhizhen.zheng@rock-chips.com>
This commit is contained in:
@@ -3,6 +3,7 @@
|
||||
comment "Rockchip media platform drivers"
|
||||
|
||||
source "drivers/media/platform/rockchip/aiisp/Kconfig"
|
||||
source "drivers/media/platform/rockchip/avsp/Kconfig"
|
||||
source "drivers/media/platform/rockchip/cif/Kconfig"
|
||||
source "drivers/media/platform/rockchip/fec/Kconfig"
|
||||
source "drivers/media/platform/rockchip/flexbus_cif/Kconfig"
|
||||
|
||||
@@ -1,5 +1,6 @@
|
||||
# SPDX-License-Identifier: GPL-2.0-only
|
||||
obj-y += aiisp/
|
||||
obj-y += avsp/
|
||||
obj-y += cif/
|
||||
obj-y += fec/
|
||||
obj-y += flexbus_cif/
|
||||
|
||||
10
drivers/media/platform/rockchip/avsp/Kconfig
Normal file
10
drivers/media/platform/rockchip/avsp/Kconfig
Normal file
@@ -0,0 +1,10 @@
|
||||
# SPDX-License-Identifier: GPL-2.0
|
||||
config VIDEO_ROCKCHIP_AVSP
|
||||
tristate "Rockchip Any View Stitching Processor driver"
|
||||
depends on ARCH_ROCKCHIP || COMPILE_TEST
|
||||
default n
|
||||
help
|
||||
Support for AVSP on the rockchip SoC.
|
||||
|
||||
If you are using a Rockchip SoC with an integrated AVSP module
|
||||
and require AVSP, say Y or M here.
|
||||
4
drivers/media/platform/rockchip/avsp/Makefile
Normal file
4
drivers/media/platform/rockchip/avsp/Makefile
Normal file
@@ -0,0 +1,4 @@
|
||||
# SPDX-License-Identifier: GPL-2.0-only
|
||||
video_rkavsp-objs := avsp.o
|
||||
|
||||
obj-$(CONFIG_VIDEO_ROCKCHIP_AVSP) += video_rkavsp.o
|
||||
781
drivers/media/platform/rockchip/avsp/avsp.c
Normal file
781
drivers/media/platform/rockchip/avsp/avsp.c
Normal file
@@ -0,0 +1,781 @@
|
||||
// SPDX-License-Identifier: GPL-2.0
|
||||
/* Copyright (C) 2025 Rockchip Electronics Co., Ltd. */
|
||||
|
||||
#include <linux/version.h>
|
||||
|
||||
#include "avsp.h"
|
||||
#include "regs.h"
|
||||
|
||||
int rkavsp_log_level;
|
||||
module_param_named(debug, rkavsp_log_level, int, 0644);
|
||||
MODULE_PARM_DESC(debug, "Debug level (0-2)");
|
||||
|
||||
#if IS_LINUX_VERSION_AT_LEAST_6_1
|
||||
#define GET_SG_TABLE(mem_ops, off_buf) mem_ops->cookie(&(off_buf)->vb, (off_buf)->mem)
|
||||
#else
|
||||
#define GET_SG_TABLE(mem_ops, off_buf) mem_ops->cookie((off_buf)->mem)
|
||||
#endif
|
||||
|
||||
static void rkavsp_soft_reset(struct rkavsp_dev *hw);
|
||||
|
||||
#if IS_LINUX_VERSION_AT_LEAST_6_1
|
||||
static void init_vb2(struct rkavsp_dev *avsp, struct rkavsp_buf *buf)
|
||||
{
|
||||
unsigned long attrs = DMA_ATTR_NO_KERNEL_MAPPING;
|
||||
|
||||
if (!buf)
|
||||
return;
|
||||
memset(&buf->vb, 0, sizeof(buf->vb));
|
||||
memset(&buf->vb2_queue, 0, sizeof(buf->vb2_queue));
|
||||
buf->vb2_queue.gfp_flags = GFP_KERNEL | GFP_DMA32;
|
||||
buf->vb2_queue.dma_dir = DMA_BIDIRECTIONAL;
|
||||
if (avsp->is_dma_config)
|
||||
attrs |= DMA_ATTR_FORCE_CONTIGUOUS;
|
||||
buf->vb2_queue.dma_attrs = attrs;
|
||||
buf->vb.vb2_queue = &buf->vb2_queue;
|
||||
}
|
||||
#endif
|
||||
|
||||
static struct rkavsp_buf *avsp_buf_add(struct file *file, int fd)
|
||||
{
|
||||
struct rkavsp_dev *avsp = container_of(file->private_data, struct rkavsp_dev, mdev);
|
||||
struct rkavsp_buf *buf = NULL, *next = NULL;
|
||||
const struct vb2_mem_ops *ops = avsp->mem_ops;
|
||||
struct dma_buf *dbuf = NULL;
|
||||
void *mem = NULL;
|
||||
bool need_add = true;
|
||||
|
||||
dbuf = dma_buf_get(fd);
|
||||
if (IS_ERR_OR_NULL(dbuf)) {
|
||||
RKAVSP_ERR("dma buf get err.\n");
|
||||
return buf;
|
||||
}
|
||||
|
||||
mutex_lock(&avsp->dev_lock);
|
||||
list_for_each_entry_safe(buf, next, &avsp->list, list) {
|
||||
if (buf->file == file && buf->fd == fd && buf->dbuf == dbuf) {
|
||||
need_add = false;
|
||||
break;
|
||||
}
|
||||
}
|
||||
|
||||
if (need_add) {
|
||||
buf = kzalloc(sizeof(struct rkavsp_buf), GFP_KERNEL);
|
||||
if (!buf)
|
||||
goto err;
|
||||
#if IS_LINUX_VERSION_AT_LEAST_6_1
|
||||
init_vb2(avsp, buf);
|
||||
|
||||
mem = ops->attach_dmabuf(&buf->vb, avsp->dev, dbuf, dbuf->size);
|
||||
#else
|
||||
mem = ops->attach_dmabuf(avsp->dev, dbuf, dbuf->size,
|
||||
DMA_BIDIRECTIONAL);
|
||||
#endif
|
||||
if (IS_ERR(mem)) {
|
||||
RKAVSP_ERR("failed to attach dmabuf.\n");
|
||||
goto err;
|
||||
}
|
||||
|
||||
if (ops->map_dmabuf(mem)) {
|
||||
RKAVSP_ERR("failed to map.\n");
|
||||
ops->detach_dmabuf(mem);
|
||||
mem = NULL;
|
||||
goto err;
|
||||
}
|
||||
|
||||
buf->fd = fd;
|
||||
buf->file = file;
|
||||
buf->dbuf = dbuf;
|
||||
buf->mem = mem;
|
||||
/* internal_alloc already add */
|
||||
buf->alloc = false;
|
||||
list_add_tail(&buf->list, &avsp->list);
|
||||
RKAVSP_DBG("file:%p fd:%d dbuf:%p\n", file, fd, dbuf);
|
||||
} else {
|
||||
dma_buf_put(dbuf);
|
||||
}
|
||||
mutex_unlock(&avsp->dev_lock);
|
||||
return buf;
|
||||
err:
|
||||
dma_buf_put(dbuf);
|
||||
kfree(buf);
|
||||
buf = NULL;
|
||||
mutex_unlock(&avsp->dev_lock);
|
||||
return buf;
|
||||
}
|
||||
|
||||
static void avsp_buf_del(struct file *file, int fd, bool is_all)
|
||||
{
|
||||
struct rkavsp_dev *avsp = container_of(file->private_data, struct rkavsp_dev, mdev);
|
||||
struct rkavsp_buf *buf, *next;
|
||||
const struct vb2_mem_ops *ops = avsp->mem_ops;
|
||||
|
||||
mutex_lock(&avsp->dev_lock);
|
||||
list_for_each_entry_safe(buf, next, &avsp->list, list) {
|
||||
if (buf->file == file && (is_all || buf->fd == fd)) {
|
||||
RKAVSP_DBG("file:%p fd:%d dbuf:%p\n", file, buf->fd, buf->dbuf);
|
||||
if (!buf->alloc) {
|
||||
ops->unmap_dmabuf(buf->mem);
|
||||
ops->detach_dmabuf(buf->mem);
|
||||
} else {
|
||||
ops->put(buf->mem);
|
||||
}
|
||||
dma_buf_put(buf->dbuf);
|
||||
buf->file = NULL;
|
||||
buf->mem = NULL;
|
||||
buf->dbuf = NULL;
|
||||
buf->fd = -1;
|
||||
list_del(&buf->list);
|
||||
kfree(buf);
|
||||
if (!is_all)
|
||||
break;
|
||||
}
|
||||
}
|
||||
mutex_unlock(&avsp->dev_lock);
|
||||
}
|
||||
|
||||
static int avsp_dcp_run(struct file *file, struct rkavsp_dcp_in_out *buf)
|
||||
{
|
||||
struct rkavsp_dev *avsp = container_of(file->private_data, struct rkavsp_dev, mdev);
|
||||
void __iomem *base = avsp->base;
|
||||
const struct vb2_mem_ops *mem_ops = avsp->mem_ops;
|
||||
struct sg_table *sgt;
|
||||
struct rkavsp_buf *off_buf;
|
||||
int ret = -EINVAL;
|
||||
int pry_h[6], i;
|
||||
u32 in_offs, out_offs, val;
|
||||
u32 in_w = buf->in_width, in_h = buf->in_height;
|
||||
u32 dcp_bypass = AVSP_BYPASS_OFF;
|
||||
u32 bandnum = buf->bandnum;
|
||||
u32 wr_mode = buf->dcp_wr_mode, rd_mode = buf->dcp_rd_mode;
|
||||
u32 dcp_rd_stride_y = buf->dcp_rd_stride_y, dcp_rd_stride_c = buf->dcp_rd_stride_c;
|
||||
|
||||
mutex_lock(&avsp->dcp_lock);
|
||||
if (rd_mode != AVSP_MODE_QUAD && rd_mode != AVSP_MODE_RASTER) {
|
||||
RKAVSP_ERR("dcp rd_mode err.\n");
|
||||
mutex_unlock(&avsp->dcp_lock);
|
||||
return -EINVAL;
|
||||
}
|
||||
|
||||
switch (buf->dcp_wr_mode) {
|
||||
case AVSP_MODE_RASTER:
|
||||
dcp_bypass = AVSP_BYPASS_OPEN;
|
||||
break;
|
||||
case AVSP_MODE_QUAD:
|
||||
break;
|
||||
default:
|
||||
RKAVSP_ERR("no support dcp_wr_mode.\n");
|
||||
mutex_unlock(&avsp->dcp_lock);
|
||||
return -EINVAL;
|
||||
}
|
||||
|
||||
// DCP CTL SET
|
||||
val = SW_DCP_BYPASS(dcp_bypass) | SW_DCP_WR_MODE(wr_mode) |
|
||||
SW_DCP_RD_MODE(rd_mode) | SW_DCP_BAND_NUM(bandnum);
|
||||
writel(val, base + AVSP_DCP_CTRL);
|
||||
val = SW_AVSP_SRC_WIDTH(in_w) | Sw_AVSP_SRC_HEIGHT(in_h);
|
||||
writel(val, base + AVSP_DCP_SIZE);
|
||||
val = AVSP_RD_VIR_STRIDE_Y(dcp_rd_stride_y) | AVSP_RD_VIR_STRIDE_C(dcp_rd_stride_c);
|
||||
writel(val, base + AVSP_DCP_RD_VIR_SIZE);
|
||||
|
||||
// wr stride set
|
||||
for (i = 0; i < bandnum; i++) {
|
||||
val = AVSP_WR_VIR_STRIDE_Y(buf->dcp_wr_stride_y[i]) |
|
||||
AVSP_WR_VIR_STRIDE_C(buf->dcp_wr_stride_c[i]);
|
||||
writel(val, base + AVSP_DCP_WR_LV0_VIR_SIZE + i * 4);
|
||||
}
|
||||
|
||||
/* input picture buf */
|
||||
in_offs = dcp_rd_stride_y * in_h * 4;
|
||||
off_buf = avsp_buf_add(file, buf->in_pic_fd);
|
||||
if (!off_buf) {
|
||||
mutex_unlock(&avsp->dcp_lock);
|
||||
return -ENOMEM;
|
||||
}
|
||||
|
||||
sgt = GET_SG_TABLE(mem_ops, off_buf);
|
||||
if (!sgt)
|
||||
goto free_buf;
|
||||
val = sg_dma_address(sgt->sgl);
|
||||
writel(val, base + AVSP_DCP_RD_Y_BASE);
|
||||
if (rd_mode == AVSP_MODE_RASTER) {
|
||||
val += in_offs;
|
||||
writel(val, base + AVSP_DCP_RD_C_BASE);
|
||||
}
|
||||
|
||||
/* output pyramid buf */
|
||||
for (i = 0; i < bandnum; i++) {
|
||||
pry_h[i] = in_h / (1 << i);
|
||||
out_offs = (buf->dcp_wr_stride_y[i]) * pry_h[i] * 4;
|
||||
off_buf = avsp_buf_add(file, buf->out_pry_fd[i]);
|
||||
if (!off_buf) {
|
||||
ret = -ENOMEM;
|
||||
goto free_buf;
|
||||
}
|
||||
|
||||
sgt = GET_SG_TABLE(mem_ops, off_buf);
|
||||
if (!sgt)
|
||||
goto free_buf;
|
||||
val = sg_dma_address(sgt->sgl);
|
||||
writel(val, base + AVSP_DCP_LV0_BASE_Y + i * 4);
|
||||
|
||||
if (wr_mode == AVSP_MODE_RASTER) {
|
||||
val += out_offs;
|
||||
writel(val, base + AVSP_DCP_LV0_BASE_C + i * 4);
|
||||
}
|
||||
}
|
||||
|
||||
writel(AVSP_FORCE_UPD, base + AVSP_DCP_UPDATE);
|
||||
writel(AVSP_ST, base + AVSP_DCP_STRT);
|
||||
RKAVSP_DBG("DCP: write start success.\n");
|
||||
|
||||
ret = wait_for_completion_timeout(&avsp->dcp_cmpl, msecs_to_jiffies(300));
|
||||
if (!ret) {
|
||||
RKAVSP_ERR("IOCTL AVSP_DCP work out time.\n");
|
||||
ret = -EAGAIN;
|
||||
rkavsp_soft_reset(avsp);
|
||||
goto free_buf;
|
||||
} else {
|
||||
ret = 0;
|
||||
}
|
||||
mutex_unlock(&avsp->dcp_lock);
|
||||
return ret;
|
||||
|
||||
free_buf:
|
||||
RKAVSP_DBG("avsp_dcp free buf.\n");
|
||||
avsp_buf_del(file, 0, true);
|
||||
mutex_unlock(&avsp->dcp_lock);
|
||||
return ret;
|
||||
}
|
||||
|
||||
static int avsp_rcs_run(struct file *file, struct rkavsp_rcs_in_out *buf)
|
||||
{
|
||||
struct rkavsp_dev *avsp = container_of(file->private_data, struct rkavsp_dev, mdev);
|
||||
void __iomem *base = avsp->base;
|
||||
const struct vb2_mem_ops *mem_ops = avsp->mem_ops;
|
||||
struct rkavsp_buf *off_buf;
|
||||
struct sg_table *sgt;
|
||||
int ret = -EINVAL;
|
||||
int i;
|
||||
|
||||
u32 rd_mode = AVSP_MODE_QUAD;
|
||||
u32 out_offs, val, c_addr;
|
||||
u32 in_w = buf->in_width, in_h = buf->in_height;
|
||||
u32 bandnum = buf->bandnum;
|
||||
u32 wr_mode = buf->rcs_wr_mode;
|
||||
u32 rcs_wr_stride_y = buf->rcs_wr_stride_y, rcs_wr_stride_c = buf->rcs_wr_stride_c;
|
||||
u32 rcs_out_start_offset = buf->rcs_out_start_offset;
|
||||
|
||||
mutex_lock(&avsp->rcs_lock);
|
||||
val = SW_RCS_BAND_NUM(bandnum) | SW_RCS_RD_MODE(rd_mode) | SW_RCS_WR_MODE(wr_mode);
|
||||
if (wr_mode == AVSP_MODE_FBCE)
|
||||
val |= SW_RCS_FBCE_CTL;
|
||||
|
||||
writel(val, base + AVSP_RCS_CTRL);
|
||||
val = SW_AVSP_SRC_WIDTH(in_w) | Sw_AVSP_SRC_HEIGHT(in_h);
|
||||
writel(val, base + AVSP_RCS_SIZE);
|
||||
val = AVSP_WR_VIR_STRIDE_Y(rcs_wr_stride_y) | AVSP_WR_VIR_STRIDE_C(rcs_wr_stride_c);
|
||||
writel(val, base + AVSP_RCS_WR_STRIDE);
|
||||
|
||||
// pry input0 buf add
|
||||
for (i = 0; i < bandnum; i++) {
|
||||
off_buf = avsp_buf_add(file, buf->in_pry0_fd[i]);
|
||||
if (!off_buf) {
|
||||
ret = -ENOMEM;
|
||||
goto free_buf;
|
||||
}
|
||||
|
||||
sgt = GET_SG_TABLE(mem_ops, off_buf);
|
||||
if (!sgt)
|
||||
goto free_buf;
|
||||
val = sg_dma_address(sgt->sgl);
|
||||
writel(val, base + AVSP_RCS_C0LV0_BASE + i * 4);
|
||||
}
|
||||
|
||||
// pry input1 buf add
|
||||
for (i = 0; i < bandnum; i++) {
|
||||
off_buf = avsp_buf_add(file, buf->in_pry1_fd[i]);
|
||||
if (!off_buf) {
|
||||
ret = -ENOMEM;
|
||||
goto free_buf;
|
||||
}
|
||||
|
||||
sgt = GET_SG_TABLE(mem_ops, off_buf);
|
||||
if (!sgt)
|
||||
goto free_buf;
|
||||
val = sg_dma_address(sgt->sgl);
|
||||
writel(val, base + AVSP_RCS_C1LV0_BASE + i * 4);
|
||||
}
|
||||
|
||||
// RCS DT_LVX
|
||||
for (i = 0; i < bandnum; i++) {
|
||||
off_buf = avsp_buf_add(file, buf->dt_pry_fd[i]);
|
||||
if (!off_buf) {
|
||||
ret = -ENOMEM;
|
||||
goto free_buf;
|
||||
}
|
||||
|
||||
sgt = GET_SG_TABLE(mem_ops, off_buf);
|
||||
if (!sgt)
|
||||
goto free_buf;
|
||||
val = sg_dma_address(sgt->sgl);
|
||||
writel(val, base + AVSP_RCS_DTLV0_BASE + i * 4);
|
||||
}
|
||||
|
||||
off_buf = avsp_buf_add(file, buf->out_pic_fd);
|
||||
if (!off_buf) {
|
||||
ret = -ENOMEM;
|
||||
goto free_buf;
|
||||
}
|
||||
|
||||
sgt = GET_SG_TABLE(mem_ops, off_buf);
|
||||
if (!sgt)
|
||||
goto free_buf;
|
||||
val = sg_dma_address(sgt->sgl);
|
||||
|
||||
switch (wr_mode) {
|
||||
case AVSP_MODE_RASTER:
|
||||
out_offs = rcs_wr_stride_y * in_h * 4;
|
||||
val += rcs_out_start_offset;
|
||||
writel(val, base + AVSP_RCS_WR_Y_BASE);
|
||||
val += out_offs;
|
||||
writel(val, base + AVSP_RCS_WR_C_BASE);
|
||||
break;
|
||||
case AVSP_MODE_FBCE:
|
||||
out_offs = rcs_wr_stride_c * in_h;
|
||||
c_addr = val + (rcs_out_start_offset / 64) * 16;
|
||||
writel(c_addr, base + AVSP_RCS_WR_C_BASE);
|
||||
val += ((rcs_out_start_offset / 64) * 384);
|
||||
val += out_offs;
|
||||
writel(val, base + AVSP_RCS_WR_Y_BASE);
|
||||
break;
|
||||
default:
|
||||
val += (rcs_out_start_offset * 6);
|
||||
writel(val, base + AVSP_RCS_WR_Y_BASE);
|
||||
break;
|
||||
}
|
||||
|
||||
writel(AVSP_FORCE_UPD, base + AVSP_RCS_UPDATE);
|
||||
writel(AVSP_ST, base + AVSP_RCS_STRT);
|
||||
ret = wait_for_completion_timeout(&avsp->rcs_cmpl, msecs_to_jiffies(300));
|
||||
if (!ret) {
|
||||
RKAVSP_ERR("IOCTL AVSP_RCS work out time.\n");
|
||||
ret = -EAGAIN;
|
||||
rkavsp_soft_reset(avsp);
|
||||
goto free_buf;
|
||||
} else {
|
||||
ret = 0;
|
||||
}
|
||||
mutex_unlock(&avsp->rcs_lock);
|
||||
return ret;
|
||||
|
||||
free_buf:
|
||||
RKAVSP_DBG("avsp_rcs free buf.\n");
|
||||
avsp_buf_del(file, 0, true);
|
||||
mutex_unlock(&avsp->rcs_lock);
|
||||
return ret;
|
||||
}
|
||||
|
||||
static int avsp_open(struct inode *inode, struct file *file)
|
||||
{
|
||||
int ret;
|
||||
struct rkavsp_dev *avsp = container_of(file->private_data, struct rkavsp_dev, mdev);
|
||||
|
||||
mutex_lock(&avsp->dev_lock);
|
||||
ret = pm_runtime_get_sync(avsp->dev);
|
||||
mutex_unlock(&avsp->dev_lock);
|
||||
|
||||
RKAVSP_INFO("avsp: device opened.\n");
|
||||
return (ret > 0) ? 0 : ret;
|
||||
}
|
||||
|
||||
static int avsp_release(struct inode *inode, struct file *file)
|
||||
{
|
||||
struct rkavsp_dev *avsp = container_of(file->private_data, struct rkavsp_dev, mdev);
|
||||
|
||||
avsp_buf_del(file, 0, true);
|
||||
mutex_lock(&avsp->dev_lock);
|
||||
pm_runtime_put_sync(avsp->dev);
|
||||
mutex_unlock(&avsp->dev_lock);
|
||||
RKAVSP_INFO("avsp: device released.\n");
|
||||
return 0;
|
||||
}
|
||||
|
||||
static long avsp_ioctl_default(struct file *file, unsigned int cmd, unsigned long arg)
|
||||
{
|
||||
long ret = 0;
|
||||
struct rkavsp_dcp_in_out dcp_data;
|
||||
struct rkavsp_rcs_in_out rcs_data;
|
||||
|
||||
if (!arg) {
|
||||
ret = -EINVAL;
|
||||
goto out;
|
||||
}
|
||||
|
||||
switch (cmd) {
|
||||
case RKAVSP_CMD_DCP:
|
||||
if (copy_from_user(&dcp_data, (struct rkavsp_dcp_in_out __user *)arg,
|
||||
sizeof(struct rkavsp_dcp_in_out))) {
|
||||
ret = -EFAULT;
|
||||
goto out;
|
||||
}
|
||||
ret = avsp_dcp_run(file, &dcp_data);
|
||||
break;
|
||||
case RKAVSP_CMD_RCS:
|
||||
if (copy_from_user(&rcs_data, (struct rkavsp_rcs_in_out __user *)arg,
|
||||
sizeof(struct rkavsp_rcs_in_out))) {
|
||||
ret = -EFAULT;
|
||||
goto out;
|
||||
}
|
||||
ret = avsp_rcs_run(file, &rcs_data);
|
||||
break;
|
||||
default:
|
||||
ret = -EFAULT;
|
||||
}
|
||||
out:
|
||||
return ret;
|
||||
}
|
||||
|
||||
static const struct file_operations avsp_fops = {
|
||||
.owner = THIS_MODULE,
|
||||
.open = avsp_open,
|
||||
.release = avsp_release,
|
||||
.unlocked_ioctl = avsp_ioctl_default,
|
||||
};
|
||||
|
||||
static irqreturn_t avsp_dcp_irq_hdl(int irq, void *dev_id)
|
||||
{
|
||||
struct device *dev = dev_id;
|
||||
struct rkavsp_dev *avsp = dev_get_drvdata(dev);
|
||||
void __iomem *base = avsp->base;
|
||||
unsigned int mis_val;
|
||||
|
||||
mis_val = readl(base + AVSP_DCP_INT_MSK);
|
||||
writel(mis_val, base + AVSP_DCP_INT_CLR);
|
||||
|
||||
if (mis_val & DCP_INT) {
|
||||
mis_val &= (~DCP_INT);
|
||||
if (!completion_done(&avsp->dcp_cmpl)) {
|
||||
complete(&avsp->dcp_cmpl);
|
||||
RKAVSP_DBG("misval: 0x%x\n", mis_val);
|
||||
}
|
||||
}
|
||||
return IRQ_HANDLED;
|
||||
}
|
||||
|
||||
static irqreturn_t avsp_rcs_irq_hdl(int irq, void *dev_id)
|
||||
{
|
||||
struct device *dev = dev_id;
|
||||
struct rkavsp_dev *avsp = dev_get_drvdata(dev);
|
||||
void __iomem *base = avsp->base;
|
||||
unsigned int mis_val;
|
||||
|
||||
mis_val = readl(base + AVSP_RCS_INT_MSK1);
|
||||
writel(mis_val, base + AVSP_RCS_INT_CLR0);
|
||||
writel(mis_val, base + AVSP_RCS_INT_CLR1);
|
||||
|
||||
if (mis_val & RCS_INT) {
|
||||
mis_val &= (~RCS_INT);
|
||||
if (!completion_done(&avsp->rcs_cmpl)) {
|
||||
complete(&avsp->rcs_cmpl);
|
||||
RKAVSP_DBG("misval: 0x%x\n", mis_val);
|
||||
}
|
||||
}
|
||||
return IRQ_HANDLED;
|
||||
}
|
||||
|
||||
static const char * const rv1126b_avsp_clks[] = {
|
||||
"aclk_avsp",
|
||||
"hclk_avsp",
|
||||
};
|
||||
|
||||
static void rkavsp_set_clk_rate(struct clk *clk, unsigned long rate)
|
||||
{
|
||||
clk_set_rate(clk, rate);
|
||||
}
|
||||
|
||||
static void disable_sys_clk(struct rkavsp_dev *dev)
|
||||
{
|
||||
int i;
|
||||
|
||||
for (i = 0; i < dev->clks_num; i++)
|
||||
clk_disable_unprepare(dev->clks[i]);
|
||||
}
|
||||
|
||||
static int enable_sys_clk(struct rkavsp_dev *dev)
|
||||
{
|
||||
int i, ret;
|
||||
|
||||
for (i = 0; i < dev->clks_num; i++) {
|
||||
ret = clk_prepare_enable(dev->clks[i]);
|
||||
if (ret < 0)
|
||||
goto err;
|
||||
}
|
||||
|
||||
//tosee
|
||||
rkavsp_set_clk_rate(dev->clks[0],
|
||||
dev->clk_rate_tbl[dev->clk_rate_tbl_num - 1].clk_rate * 1000000);
|
||||
|
||||
return 0;
|
||||
|
||||
err:
|
||||
for (--i; i >= 0; --i)
|
||||
clk_disable_unprepare(dev->clks[i]);
|
||||
return ret;
|
||||
}
|
||||
|
||||
static int avsp_probe(struct platform_device *pdev)
|
||||
{
|
||||
const struct avsp_match_data *match_data;
|
||||
struct rkavsp_dev *avsp;
|
||||
struct device *dev = &pdev->dev;
|
||||
struct resource *res;
|
||||
int i, irq, ret = 0;
|
||||
//bool is_mmu;
|
||||
|
||||
match_data = device_get_match_data(&pdev->dev);
|
||||
if (!match_data)
|
||||
return -ENODEV;
|
||||
|
||||
avsp = devm_kzalloc(&pdev->dev, sizeof(*avsp), GFP_KERNEL);
|
||||
if (!avsp)
|
||||
return -ENOMEM;
|
||||
|
||||
dev_set_drvdata(dev, avsp);
|
||||
avsp->dev = &pdev->dev;
|
||||
avsp->match_data = match_data;
|
||||
|
||||
/* map the registers */
|
||||
res = platform_get_resource(pdev, IORESOURCE_MEM, 0);
|
||||
if (!res) {
|
||||
RKAVSP_ERR("get memory resource failed.\n");
|
||||
ret = -EINVAL;
|
||||
goto err;
|
||||
}
|
||||
|
||||
avsp->base = devm_ioremap_resource(avsp->dev, res);
|
||||
if (IS_ERR(avsp->base)) {
|
||||
RKAVSP_ERR("ioremap failed\n");
|
||||
ret = PTR_ERR(avsp->base);
|
||||
goto err;
|
||||
}
|
||||
|
||||
INIT_LIST_HEAD(&avsp->list);
|
||||
init_completion(&avsp->dcp_cmpl);
|
||||
init_completion(&avsp->rcs_cmpl);
|
||||
avsp->mem_ops = &vb2_cma_sg_memops;
|
||||
|
||||
/* get the irq */
|
||||
for (i = 0; i < match_data->num_irqs; i++) {
|
||||
irq = platform_get_irq_byname(pdev, match_data->irqs[i].name);
|
||||
if (irq < 0) {
|
||||
RKAVSP_ERR("no irq %s in dts.\n", match_data->irqs[i].name);
|
||||
ret = irq;
|
||||
goto err;
|
||||
}
|
||||
ret = devm_request_irq(dev, irq, match_data->irqs[i].irq_hdl,
|
||||
IRQF_SHARED, dev_driver_string(dev), dev);
|
||||
if (ret < 0) {
|
||||
RKAVSP_ERR("request %s failed: %d\n", match_data->irqs[i].name, ret);
|
||||
goto err;
|
||||
}
|
||||
}
|
||||
/* get the clk */
|
||||
for (i = 0; i < match_data->clks_num; i++) {
|
||||
struct clk *clk = devm_clk_get(dev, match_data->clks[i]);
|
||||
|
||||
if (IS_ERR(clk)) {
|
||||
RKAVSP_ERR("failed to get %s\n", match_data->clks[i]);
|
||||
ret = PTR_ERR(clk);
|
||||
goto err;
|
||||
}
|
||||
avsp->clks[i] = clk;
|
||||
}
|
||||
avsp->clks_num = match_data->clks_num;
|
||||
avsp->clk_rate_tbl = match_data->clk_rate_tbl;
|
||||
avsp->clk_rate_tbl_num = match_data->clk_rate_tbl_num;
|
||||
|
||||
avsp->reset = devm_reset_control_array_get(dev, false, false);
|
||||
if (IS_ERR(avsp->reset)) {
|
||||
RKAVSP_INFO("failed to get cru reset\n");
|
||||
avsp->reset = NULL;
|
||||
}
|
||||
|
||||
mutex_init(&avsp->dev_lock);
|
||||
mutex_init(&avsp->dcp_lock);
|
||||
mutex_init(&avsp->rcs_lock);
|
||||
avsp->is_dma_config = true;
|
||||
|
||||
// register misc device
|
||||
avsp->mdev.minor = MISC_DYNAMIC_MINOR;
|
||||
avsp->mdev.name = AVSP_NAME;
|
||||
avsp->mdev.fops = &avsp_fops;
|
||||
|
||||
ret = misc_register(&avsp->mdev);
|
||||
if (ret < 0) {
|
||||
RKAVSP_ERR("avsp misc register failed.\n");
|
||||
goto err;
|
||||
}
|
||||
|
||||
pm_runtime_enable(&pdev->dev);
|
||||
RKAVSP_INFO("avsp misc device probe success.\n");
|
||||
return 0;
|
||||
err:
|
||||
return ret;
|
||||
}
|
||||
|
||||
static int avsp_remove(struct platform_device *pdev)
|
||||
{
|
||||
/* misc device remove */
|
||||
struct rkavsp_dev *avsp = platform_get_drvdata(pdev);
|
||||
|
||||
pm_runtime_disable(&pdev->dev);
|
||||
misc_deregister(&avsp->mdev);
|
||||
mutex_destroy(&avsp->rcs_lock);
|
||||
mutex_destroy(&avsp->dcp_lock);
|
||||
mutex_destroy(&avsp->dev_lock);
|
||||
|
||||
return 0;
|
||||
}
|
||||
|
||||
static const struct avsp_clk_info rv1126b_avsp_clk_rate[] = {
|
||||
{
|
||||
.clk_rate = 300,
|
||||
.refer_data = 1920,
|
||||
}, {
|
||||
.clk_rate = 400,
|
||||
.refer_data = 2688,
|
||||
}, {
|
||||
.clk_rate = 500,
|
||||
.refer_data = 3072,
|
||||
}, {
|
||||
.clk_rate = 600,
|
||||
.refer_data = 3840,
|
||||
}, {
|
||||
.clk_rate = 702,
|
||||
.refer_data = 4672,
|
||||
}
|
||||
};
|
||||
|
||||
static struct irqs_data rv1126b_avsp_irqs[] = {
|
||||
{"dcp_irq", avsp_dcp_irq_hdl},
|
||||
{"rcs_irq", avsp_rcs_irq_hdl},
|
||||
};
|
||||
|
||||
static const struct avsp_match_data rv1126b_avsp_match_data = {
|
||||
.clks = rv1126b_avsp_clks,
|
||||
.clks_num = ARRAY_SIZE(rv1126b_avsp_clks),
|
||||
.clk_rate_tbl = rv1126b_avsp_clk_rate,
|
||||
.clk_rate_tbl_num = ARRAY_SIZE(rv1126b_avsp_clk_rate),
|
||||
.irqs = rv1126b_avsp_irqs,
|
||||
.num_irqs = ARRAY_SIZE(rv1126b_avsp_irqs),
|
||||
};
|
||||
|
||||
static const struct of_device_id rockchip_avsp_match[] = {
|
||||
{
|
||||
.compatible = "rockchip,rv1126b-rkavsp",
|
||||
.data = &rv1126b_avsp_match_data,
|
||||
},
|
||||
{},
|
||||
};
|
||||
|
||||
MODULE_DEVICE_TABLE(of, rockchip_avsp_match);
|
||||
|
||||
static void rkavsp_soft_reset(struct rkavsp_dev *hw)
|
||||
{
|
||||
u32 val;
|
||||
|
||||
/* reset */
|
||||
val = SYS_SOFT_RST_DCP;
|
||||
writel(val, hw->base + AVSP_DCP_CLK_DIS);
|
||||
udelay(10);
|
||||
writel(SYS_SOFT_RST_VAL, hw->base + AVSP_DCP_CLK_DIS);
|
||||
|
||||
if (hw->reset) {
|
||||
reset_control_assert(hw->reset);
|
||||
udelay(20);
|
||||
reset_control_deassert(hw->reset);
|
||||
udelay(20);
|
||||
}
|
||||
|
||||
/* refresh iommu after reset */
|
||||
rockchip_iommu_disable(hw->dev);
|
||||
rockchip_iommu_enable(hw->dev);
|
||||
|
||||
/* clk_dis */
|
||||
val = SYS_DCP_LGC_CKG_DIS | SYS_DCP_RAM_CKG_DIS;
|
||||
writel(val, hw->base + AVSP_DCP_CLK_DIS);
|
||||
|
||||
/* int en */
|
||||
val = DCP_INT;
|
||||
writel(val, hw->base + AVSP_DCP_INT_EN);
|
||||
val = RCS_INT;
|
||||
writel(val, hw->base + AVSP_RCS_INT_EN1);
|
||||
}
|
||||
|
||||
static int __maybe_unused rkavsp_runtime_suspend(struct device *dev)
|
||||
{
|
||||
struct rkavsp_dev *avsp = dev_get_drvdata(dev);
|
||||
|
||||
if (dev->power.runtime_status) {
|
||||
writel(0, avsp->base + AVSP_DCP_INT_EN);
|
||||
writel(0, avsp->base + AVSP_RCS_INT_EN1);
|
||||
}
|
||||
|
||||
disable_sys_clk(avsp);
|
||||
return 0;
|
||||
}
|
||||
|
||||
static int __maybe_unused rkavsp_runtime_resume(struct device *dev)
|
||||
{
|
||||
struct rkavsp_dev *avsp = dev_get_drvdata(dev);
|
||||
|
||||
enable_sys_clk(avsp);
|
||||
rkavsp_soft_reset(avsp);
|
||||
|
||||
//if (dev->power.runtime_status)
|
||||
return 0;
|
||||
}
|
||||
|
||||
static const struct dev_pm_ops rkavsp_pm_ops = {
|
||||
SET_LATE_SYSTEM_SLEEP_PM_OPS(pm_runtime_force_suspend,
|
||||
pm_runtime_force_resume)
|
||||
SET_RUNTIME_PM_OPS(rkavsp_runtime_suspend,
|
||||
rkavsp_runtime_resume, NULL)
|
||||
};
|
||||
|
||||
static void rkavsp_shutdown(struct platform_device *pdev)
|
||||
{
|
||||
struct rkavsp_dev *avsp = platform_get_drvdata(pdev);
|
||||
u32 val;
|
||||
|
||||
//hw_dev->is_shutdown = true;
|
||||
if (pm_runtime_active(&pdev->dev)) {
|
||||
writel(0, avsp->base + AVSP_DCP_INT_EN);
|
||||
writel(0, avsp->base + AVSP_RCS_INT_EN1);
|
||||
|
||||
val = SYS_SOFT_RST_DCP;
|
||||
writel(val, avsp->base + AVSP_DCP_CLK_DIS);
|
||||
udelay(10);
|
||||
writel(SYS_SOFT_RST_VAL, avsp->base + AVSP_DCP_CLK_DIS);
|
||||
}
|
||||
RKAVSP_INFO("shutdown.\n");
|
||||
}
|
||||
|
||||
static struct platform_driver avsp_pdrv = {
|
||||
.probe = avsp_probe,
|
||||
.remove = avsp_remove,
|
||||
.shutdown = rkavsp_shutdown,
|
||||
.driver = {
|
||||
.name = AVSP_NAME,
|
||||
.pm = &rkavsp_pm_ops,
|
||||
.of_match_table = of_match_ptr(rockchip_avsp_match),
|
||||
},
|
||||
};
|
||||
|
||||
module_platform_driver(avsp_pdrv);
|
||||
|
||||
MODULE_AUTHOR("Zhizhen Zheng <zhizhen.zheng@rock-chips.com>");
|
||||
MODULE_DESCRIPTION("Rockchip AVSP Module");
|
||||
MODULE_LICENSE("GPL");
|
||||
MODULE_IMPORT_NS(DMA_BUF);
|
||||
149
drivers/media/platform/rockchip/avsp/avsp.h
Normal file
149
drivers/media/platform/rockchip/avsp/avsp.h
Normal file
@@ -0,0 +1,149 @@
|
||||
/* SPDX-License-Identifier: GPL-2.0 */
|
||||
/* Copyright (C) 2025 Rockchip Electronics Co., Ltd. */
|
||||
|
||||
#ifndef __RKAVSP_H__
|
||||
#define __RKAVSP_H__
|
||||
|
||||
#include <linux/clk.h>
|
||||
#include <linux/debugfs.h>
|
||||
#include <linux/delay.h>
|
||||
#include <linux/fs.h>
|
||||
#include <linux/interrupt.h>
|
||||
#include <linux/module.h>
|
||||
#include <linux/of.h>
|
||||
#include <linux/pm_runtime.h>
|
||||
#include <linux/reset.h>
|
||||
#include <linux/sched.h>
|
||||
#include <linux/slab.h>
|
||||
#include <linux/timer.h>
|
||||
#include <linux/platform_device.h>
|
||||
#include <linux/miscdevice.h>
|
||||
#include <media/videobuf2-cma-sg.h>
|
||||
#include <media/videobuf2-dma-sg.h>
|
||||
#include <linux/iommu.h>
|
||||
#include <soc/rockchip/rockchip_iommu.h>
|
||||
|
||||
extern int rkavsp_log_level;
|
||||
|
||||
#define RKAVSP_LEVEL_ERR 0
|
||||
#define RKAVSP_LEVEL_INFO 1
|
||||
#define RKAVSP_LEVEL_DBG 2
|
||||
|
||||
#define RKAVSP_PRINT(level, fmt, args...) \
|
||||
do { \
|
||||
if (rkavsp_log_level >= level) { \
|
||||
if (level == RKAVSP_LEVEL_ERR) \
|
||||
dev_err(avsp->dev, "%s:%d " fmt, __func__, __LINE__, ##args); \
|
||||
else if (level == RKAVSP_LEVEL_INFO) \
|
||||
dev_info(avsp->dev, "%s:%d " fmt, __func__, __LINE__, ##args); \
|
||||
else if (level == RKAVSP_LEVEL_DBG) \
|
||||
dev_dbg(avsp->dev, "%s:%d " fmt, __func__, __LINE__, ##args); \
|
||||
} \
|
||||
} while (0)
|
||||
|
||||
#define RKAVSP_ERR(fmt, args...) RKAVSP_PRINT(RKAVSP_LEVEL_ERR, fmt, ##args)
|
||||
#define RKAVSP_INFO(fmt, args...) RKAVSP_PRINT(RKAVSP_LEVEL_INFO, fmt, ##args)
|
||||
#define RKAVSP_DBG(fmt, args...) RKAVSP_PRINT(RKAVSP_LEVEL_DBG, fmt, ##args)
|
||||
|
||||
#define RKAVSP_CMD_DCP \
|
||||
_IOW('V', 192 + 20, struct rkavsp_dcp_in_out)
|
||||
|
||||
#define RKAVSP_CMD_RCS \
|
||||
_IOW('V', 192 + 21, struct rkavsp_rcs_in_out)
|
||||
|
||||
#define AVSP_NAME "rockchip_avsp"
|
||||
#define AVSP_MAX_BUS_CLK 3
|
||||
|
||||
struct rkavsp_buf {
|
||||
int fd;
|
||||
struct file *file;
|
||||
struct list_head list;
|
||||
struct vb2_buffer vb;
|
||||
struct vb2_queue vb2_queue;
|
||||
struct dma_buf *dbuf;
|
||||
struct dma_buf_attachment *dba;
|
||||
void *mem;
|
||||
bool alloc;
|
||||
};
|
||||
|
||||
struct avsp_match_data {
|
||||
int clks_num;
|
||||
const char * const *clks;
|
||||
int clk_rate_tbl_num;
|
||||
const struct avsp_clk_info *clk_rate_tbl;
|
||||
struct irqs_data *irqs;
|
||||
int num_irqs;
|
||||
};
|
||||
|
||||
struct rkavsp_dev {
|
||||
struct device *dev;
|
||||
struct regmap *grf;
|
||||
struct completion dcp_cmpl;
|
||||
struct completion rcs_cmpl;
|
||||
struct list_head list;
|
||||
const struct vb2_mem_ops *mem_ops;
|
||||
void __iomem *base;
|
||||
struct reset_control *reset;
|
||||
const struct avsp_match_data *match_data;
|
||||
const struct avsp_clk_info *clk_rate_tbl;
|
||||
struct clk *clks[AVSP_MAX_BUS_CLK];
|
||||
int clk_rate_tbl_num;
|
||||
int clks_num;
|
||||
|
||||
spinlock_t dcp_irq_lock;
|
||||
spinlock_t rcs_irq_lock;
|
||||
struct mutex dev_lock;
|
||||
struct mutex dcp_lock;
|
||||
struct mutex rcs_lock;
|
||||
struct miscdevice mdev;
|
||||
bool is_dma_config;
|
||||
|
||||
};
|
||||
|
||||
struct rkavsp_dcp_in_out {
|
||||
int in_width;
|
||||
int in_height;
|
||||
int bandnum;
|
||||
int dcp_rd_mode;
|
||||
int dcp_wr_mode;
|
||||
|
||||
int dcp_rd_stride_y;
|
||||
int dcp_rd_stride_c;
|
||||
int dcp_wr_stride_y[6];
|
||||
int dcp_wr_stride_c[6];
|
||||
|
||||
int in_pic_fd;
|
||||
int out_pry_fd[6];
|
||||
};
|
||||
|
||||
struct rkavsp_rcs_in_out {
|
||||
int in_width;
|
||||
int in_height;
|
||||
int bandnum;
|
||||
|
||||
int rcs_wr_mode;
|
||||
int rcs_wr_stride_y;
|
||||
int rcs_wr_stride_c;
|
||||
|
||||
int in_pry0_fd[6];
|
||||
int in_pry1_fd[6];
|
||||
int dt_pry_fd[6];
|
||||
int out_pic_fd;
|
||||
int rcs_out_start_offset;
|
||||
};
|
||||
|
||||
struct avsp_clk_info {
|
||||
u32 clk_rate;
|
||||
u32 refer_data;
|
||||
};
|
||||
|
||||
struct irqs_data {
|
||||
const char *name;
|
||||
irqreturn_t (*irq_hdl)(int irq, void *ctx);
|
||||
};
|
||||
|
||||
#ifndef IS_LINUX_VERSION_AT_LEAST_6_1
|
||||
#define IS_LINUX_VERSION_AT_LEAST_6_1 (KERNEL_VERSION(6, 1, 0) <= LINUX_VERSION_CODE)
|
||||
#endif
|
||||
|
||||
#endif
|
||||
143
drivers/media/platform/rockchip/avsp/regs.h
Normal file
143
drivers/media/platform/rockchip/avsp/regs.h
Normal file
@@ -0,0 +1,143 @@
|
||||
/* SPDX-License-Identifier: GPL-2.0 */
|
||||
/* Copyright (C) 2025 Rockchip Electronics Co., Ltd. */
|
||||
|
||||
#ifndef _RKAVSP_REGS_H
|
||||
#define _RKAVSP_REGS_H
|
||||
|
||||
#define ALIGN_RASTER(w) (((w + 15) / 16) * 16)
|
||||
#define ALIGN_QUAD(w) (((w * 3 + 15) / 16) * 16)
|
||||
|
||||
#define DCP_STD_MSK 0x3FFF
|
||||
#define AVSP_FORCE_UPD 0x1
|
||||
#define AVSP_ST 0x1
|
||||
#define AVSP_BYPASS_OPEN 0x1
|
||||
#define AVSP_BYPASS_OFF 0x0
|
||||
|
||||
/* AVSP FMT DEFINE */
|
||||
#define AVSP_MODE_RASTER 0x0
|
||||
#define AVSP_MODE_TILE 0x1
|
||||
#define AVSP_MODE_FBCE 0x2
|
||||
#define AVSP_MODE_QUAD 0x3
|
||||
|
||||
/* AVSP_DCP_CORE_CTRL */
|
||||
#define SW_DCP_BYPASS(x) ((x & 0x1) << 7)
|
||||
#define SW_DCP_WR_MODE(x) ((x & 0x3) << 5)
|
||||
#define SW_DCP_RD_MODE(x) ((x & 0x3) << 3)
|
||||
#define SW_DCP_BAND_NUM(x) (x & 0x7)
|
||||
|
||||
/* AVSP_SRC_SIZE */
|
||||
#define SW_AVSP_SRC_WIDTH(x) ((x) & 0x07ff)
|
||||
#define Sw_AVSP_SRC_HEIGHT(x) (((x) & 0x1fff) << 16)
|
||||
|
||||
/* AVSP_RD_VIR_STRIDE */
|
||||
#define AVSP_RD_VIR_STRIDE_Y(x) ((x) & 0x3fff)
|
||||
#define AVSP_RD_VIR_STRIDE_C(x) (((x) & 0x3fff) << 16)
|
||||
|
||||
/* AVSP_WR_VIR_STRIDE */
|
||||
#define AVSP_WR_VIR_STRIDE_Y(x) ((x) & 0x3fff)
|
||||
#define AVSP_WR_VIR_STRIDE_C(x) (((x) & 0x3fff) << 16)
|
||||
|
||||
/* AVSP_RCS_CORE_CTRL */
|
||||
#define SW_RCS_WR_MODE(x) ((x & 0x3) << 5)
|
||||
#define SW_RCS_RD_MODE(x) ((x & 0x3) << 3)
|
||||
#define SW_RCS_BAND_NUM(x) (x & 0x7)
|
||||
#define SW_RCS_FBCE_CTL (0x6 << 9)
|
||||
|
||||
// AVSP INT
|
||||
#define DCP_INT (0x1 << 25)
|
||||
#define RCS_INT 0x00010000
|
||||
#define SYS_SOFT_RST_DCP 0x00004000
|
||||
#define SYS_SOFT_RST_VAL 0x00000000
|
||||
#define SYS_DCP_LGC_CKG_DIS 0x00000001
|
||||
#define SYS_DCP_RAM_CKG_DIS 0x00000002
|
||||
|
||||
/* AVSP_REGS */
|
||||
#define AVSP_BASE 0x00000000
|
||||
|
||||
#define AVSP_DCP_STRT (AVSP_BASE + 0x00300)
|
||||
#define AVSP_DCP_UPDATE (AVSP_BASE + 0x00304)
|
||||
#define AVSP_DCP_CLK_DIS (AVSP_BASE + 0x00308)
|
||||
#define AVSP_DCP_CTRL (AVSP_BASE + 0x00310)
|
||||
#define AVSP_DCP_SIZE (AVSP_BASE + 0x00314)
|
||||
#define AVSP_DCP_RD_VIR_SIZE (AVSP_BASE + 0x00318)
|
||||
#define AVSP_DCP_WR_LV0_VIR_SIZE (AVSP_BASE + 0x0031c)
|
||||
#define AVSP_DCP_WR_LV1_VIR_SIZE (AVSP_BASE + 0x00320)
|
||||
#define AVSP_DCP_WR_LV2_VIR_SIZE (AVSP_BASE + 0x00324)
|
||||
#define AVSP_DCP_WR_LV3_VIR_SIZE (AVSP_BASE + 0x00328)
|
||||
#define AVSP_DCP_WR_LV4_VIR_SIZE (AVSP_BASE + 0x0032c)
|
||||
#define AVSP_DCP_WR_LV5_VIR_SIZE (AVSP_BASE + 0x00330)
|
||||
#define AVSP_DCP_RD_Y_BASE (AVSP_BASE + 0x00334)
|
||||
#define AVSP_DCP_RD_C_BASE (AVSP_BASE + 0x00338)
|
||||
#define AVSP_DCP_LV0_BASE_Y (AVSP_BASE + 0x0033c)
|
||||
#define AVSP_DCP_LV1_BASE_Y (AVSP_BASE + 0x00340)
|
||||
#define AVSP_DCP_LV2_BASE_Y (AVSP_BASE + 0x00344)
|
||||
#define AVSP_DCP_LV3_BASE_Y (AVSP_BASE + 0x00348)
|
||||
#define AVSP_DCP_LV4_BASE_Y (AVSP_BASE + 0x0034c)
|
||||
#define AVSP_DCP_LV5_BASE_Y (AVSP_BASE + 0x00350)
|
||||
#define AVSP_DCP_LV0_BASE_C (AVSP_BASE + 0x00354)
|
||||
#define AVSP_DCP_LV1_BASE_C (AVSP_BASE + 0x00358)
|
||||
#define AVSP_DCP_LV2_BASE_C (AVSP_BASE + 0x0035c)
|
||||
#define AVSP_DCP_LV3_BASE_C (AVSP_BASE + 0x00360)
|
||||
#define AVSP_DCP_LV4_BASE_C (AVSP_BASE + 0x00364)
|
||||
#define AVSP_DCP_LV5_BASE_C (AVSP_BASE + 0x00368)
|
||||
#define AVSP_DCP_INT_EN (AVSP_BASE + 0x00390)
|
||||
#define AVSP_DCP_INT_CLR (AVSP_BASE + 0x00394)
|
||||
#define AVSP_DCP_INT_RAW (AVSP_BASE + 0x00398)
|
||||
#define AVSP_DCP_INT_MSK (AVSP_BASE + 0x0039c)
|
||||
#define AVSP_DCP_STATUS0 (AVSP_BASE + 0x003a0)
|
||||
#define AVSP_DCP_STATUS1 (AVSP_BASE + 0x003a4)
|
||||
#define AVSP_DCP_STATUS2 (AVSP_BASE + 0x003a8)
|
||||
#define AVSP_DCP_STATUS3 (AVSP_BASE + 0x003ac)
|
||||
#define AVSP_DCP_STATUS4 (AVSP_BASE + 0x003b0)
|
||||
#define AVSP_RCS_STRT (AVSP_BASE + 0x00400)
|
||||
#define AVSP_RCS_UPDATE (AVSP_BASE + 0x00404)
|
||||
#define AVSP_RCS_CLK_DIS (AVSP_BASE + 0x00408)
|
||||
#define AVSP_RCS_CTRL (AVSP_BASE + 0x00410)
|
||||
#define AVSP_RCS_SIZE (AVSP_BASE + 0x00414)
|
||||
#define AVSP_RCS_WR_STRIDE (AVSP_BASE + 0x00430)
|
||||
#define AVSP_RCS_C0LV0_BASE (AVSP_BASE + 0x00434)
|
||||
#define AVSP_RCS_C0LV1_BASE (AVSP_BASE + 0x00438)
|
||||
#define AVSP_RCS_C0LV2_BASE (AVSP_BASE + 0x0043c)
|
||||
#define AVSP_RCS_C0LV3_BASE (AVSP_BASE + 0x00440)
|
||||
#define AVSP_RCS_C0LV4_BASE (AVSP_BASE + 0x00444)
|
||||
#define AVSP_RCS_C0LV5_BASE (AVSP_BASE + 0x00448)
|
||||
#define AVSP_RCS_C1LV0_BASE (AVSP_BASE + 0x0044c)
|
||||
#define AVSP_RCS_C1LV2_BASE (AVSP_BASE + 0x00450)
|
||||
#define AVSP_RCS_C1LV1_BASE (AVSP_BASE + 0x00454)
|
||||
#define AVSP_RCS_C1LV3_BASE (AVSP_BASE + 0x00458)
|
||||
#define AVSP_RCS_C1LV4_BASE (AVSP_BASE + 0x0045c)
|
||||
#define AVSP_RCS_C1LV5_BASE (AVSP_BASE + 0x00460)
|
||||
#define AVSP_RCS_DTLV0_BASE (AVSP_BASE + 0x00464)
|
||||
#define AVSP_RCS_DTLV1_BASE (AVSP_BASE + 0x00468)
|
||||
#define AVSP_RCS_DTLV2_BASE (AVSP_BASE + 0x0046c)
|
||||
#define AVSP_RCS_DTLV3_BASE (AVSP_BASE + 0x00470)
|
||||
#define AVSP_RCS_DTLV4_BASE (AVSP_BASE + 0x00474)
|
||||
#define AVSP_RCS_DTLV5_BASE (AVSP_BASE + 0x00478)
|
||||
#define AVSP_RCS_WR_Y_BASE (AVSP_BASE + 0x0047c)
|
||||
#define AVSP_RCS_WR_C_BASE (AVSP_BASE + 0x00480)
|
||||
#define AVSP_RCS_WR_FBCE_HEAD_OFFSET (AVSP_BASE + 0x00484)
|
||||
#define AVSP_RCS_INT_EN0 (AVSP_BASE + 0x00490)
|
||||
#define AVSP_RCS_INT_CLR0 (AVSP_BASE + 0x00494)
|
||||
#define AVSP_RCS_INT_RAW0 (AVSP_BASE + 0x00498)
|
||||
#define AVSP_RCS_INT_MSK0 (AVSP_BASE + 0x0049c)
|
||||
#define AVSP_RCS_INT_EN1 (AVSP_BASE + 0x004a0)
|
||||
#define AVSP_RCS_INT_CLR1 (AVSP_BASE + 0x004a4)
|
||||
#define AVSP_RCS_INT_RAW1 (AVSP_BASE + 0x004a8)
|
||||
#define AVSP_RCS_INT_MSK1 (AVSP_BASE + 0x004ac)
|
||||
#define AVSP_RCS_STATUS0 (AVSP_BASE + 0x004b0)
|
||||
#define AVSP_RCS_STATUS1 (AVSP_BASE + 0x004b4)
|
||||
#define AVSP_RCS_STATUS2 (AVSP_BASE + 0x004b8)
|
||||
#define AVSP_RCS_STATUS3 (AVSP_BASE + 0x004bc)
|
||||
#define MMU_DTE_ADDR (AVSP_BASE + 0x00f00)
|
||||
#define MMU_STATUS (AVSP_BASE + 0x00f04)
|
||||
#define MMU_COMMAND (AVSP_BASE + 0x00f08)
|
||||
#define MMU_PAGE_FAULT_ADDR (AVSP_BASE + 0x00f0c)
|
||||
#define MMU_ZAP_ONE_LINE (AVSP_BASE + 0x00f10)
|
||||
#define MMU_INT_RAWSTAT (AVSP_BASE + 0x00f14)
|
||||
#define MMU_INT_CLEAR (AVSP_BASE + 0x00f18)
|
||||
#define MMU_INT_MASK (AVSP_BASE + 0x00f1c)
|
||||
#define MMU_INT_STATUS (AVSP_BASE + 0x00f20)
|
||||
#define MMU_AUTO_GATING (AVSP_BASE + 0x00f24)
|
||||
#define MMU_REG_LOAD_EN (AVSP_BASE + 0x00f28)
|
||||
|
||||
#endif
|
||||
Reference in New Issue
Block a user