From cc316f1b45fc06ea490de1a214f5954ea1d7dddf Mon Sep 17 00:00:00 2001 From: Pengcheng Chen Date: Tue, 28 May 2019 17:58:42 +0800 Subject: [PATCH] ge2d: move ge2d canvas_config to ge2d process thread [1/1] PD#OTT-4320 Problem: ge2d canvas_config have been overwritten Solution: move ge2d canvas_config from ge2d config to ge2d process Verify: w400 Change-Id: I6733751435f9185c8f96287c5308145898c8b8a7 Signed-off-by: Pengcheng Chen gdc: gdc dmabuf multi-process support [1/1] PD#OTT-4320 Problem: gdc phys have been overwritten when dma fd is same from diff process Solution: when get phys by dma fd, used struct dma_buf instead of dma fd Verify: w400 Change-Id: I6e990c9fda9245db0d92053cc011fc6f9507db72 Signed-off-by: Pengcheng Chen ge2d: ge2d dmabuf multi-process support [1/1] PD#OTT-4320 Problem: ge2d phys have been overwritten when dma fd is same from diff process Solution: when get phys addr by dma fd, used struct dma_buf instead of dma fd Verify: w400 Change-Id: Idb32bc61d33345d370db4eb6bcb04351d854f069 Signed-off-by: Pengcheng Chen --- .../amlogic/media/common/ge2d/ge2d_dmabuf.c | 37 +- drivers/amlogic/media/common/ge2d/ge2d_wq.c | 602 ++++++++---------- drivers/amlogic/media/gdc/app/gdc_dmabuf.c | 36 +- include/linux/amlogic/media/ge2d/ge2d.h | 11 + 4 files changed, 341 insertions(+), 345 deletions(-) diff --git a/drivers/amlogic/media/common/ge2d/ge2d_dmabuf.c b/drivers/amlogic/media/common/ge2d/ge2d_dmabuf.c index f024876958a9..e397caa1fc2e 100644 --- a/drivers/amlogic/media/common/ge2d/ge2d_dmabuf.c +++ b/drivers/amlogic/media/common/ge2d/ge2d_dmabuf.c @@ -505,6 +505,7 @@ int ge2d_dma_buffer_export(struct aml_dma_buffer *buffer, ge2d_log_dbg("buffer %d,exported as %d descriptor\n", index, ret); buffer->gd_buffer[index].fd = ret; + buffer->gd_buffer[index].dbuf = dbuf; ge2d_exp_buf->fd = ret; return 0; } @@ -580,18 +581,28 @@ attach_err: } static int ge2d_dma_buffer_get_phys_internal(struct aml_dma_buffer *buffer, - int fd, unsigned long *addr) + struct aml_dma_cfg *cfg, unsigned long *addr) { int i = 0, ret = -1; struct aml_dma_buf *dma_buf; + struct dma_buf *dbuf = NULL; for (i = 0; i < AML_MAX_DMABUF; i++) { - if (buffer->gd_buffer[i].alloc && - (fd == buffer->gd_buffer[i].fd)) { - dma_buf = buffer->gd_buffer[i].mem_priv; - *addr = dma_buf->dma_addr; - ret = 0; - break; + if (buffer->gd_buffer[i].alloc) { + dbuf = dma_buf_get(cfg->fd); + if (IS_ERR(dbuf)) { + pr_err("%s: failed to get dma buffer,fd=%d, dbuf=%p\n", + __func__, cfg->fd, dbuf); + return -EINVAL; + } + dma_buf_put(dbuf); + if (dbuf == buffer->gd_buffer[i].dbuf) { + cfg->dbuf = dbuf; + dma_buf = buffer->gd_buffer[i].mem_priv; + *addr = dma_buf->dma_addr; + ret = 0; + break; + } } } return ret; @@ -608,7 +619,7 @@ int ge2d_dma_buffer_get_phys(struct aml_dma_buffer *buffer, pr_err("error input param"); return -EINVAL; } - ret = ge2d_dma_buffer_get_phys_internal(buffer, cfg->fd, addr); + ret = ge2d_dma_buffer_get_phys_internal(buffer, cfg, addr); if (ret < 0) { ret = ge2d_dma_buffer_map(cfg); if (ret < 0) { @@ -634,12 +645,12 @@ int ge2d_dma_buffer_unmap_info(struct aml_dma_buffer *buffer, pr_err("error input param"); return -EINVAL; } - for (i = 0; i < AML_MAX_DMABUF; i++) { - if (buffer->gd_buffer[i].alloc && - (cfg->fd == buffer->gd_buffer[i].fd)) { - found = 1; - break; + if (buffer->gd_buffer[i].alloc) { + if (cfg->dbuf == buffer->gd_buffer[i].dbuf) { + found = 1; + break; + } } } if (!found) diff --git a/drivers/amlogic/media/common/ge2d/ge2d_wq.c b/drivers/amlogic/media/common/ge2d/ge2d_wq.c index 1549b977e1bf..dc2322487e26 100644 --- a/drivers/amlogic/media/common/ge2d/ge2d_wq.c +++ b/drivers/amlogic/media/common/ge2d/ge2d_wq.c @@ -299,6 +299,86 @@ static void ge2d_dump_cmd(struct ge2d_cmd_s *cfg) ge2d_log_dbg("GE2D_STATUS1=0x%x\n", ge2d_reg_read(GE2D_STATUS1)); } +static void ge2d_set_canvas(struct ge2d_config_s *cfg) +{ + int i, index; + int index_src = 0, index_src2 = 0, index_dst = 0; + int canvas_set = 0; + + index = ALLOC_CANVAS_INDEX; + for (i = 0; i < MAX_PLANE; i++) { + if (cfg->src_canvas_cfg[i].canvas_used) { + index_src |= index << (8 * i); +#ifdef CONFIG_AMLOGIC_MEDIA_CANVAS + canvas_config(index++, + cfg->src_canvas_cfg[i].phys_addr, + cfg->src_canvas_cfg[i].stride, + cfg->src_canvas_cfg[i].height, + CANVAS_ADDR_NOWRAP, + CANVAS_BLKMODE_LINEAR); +#endif + cfg->src_canvas_cfg[i].canvas_used = 0; + ge2d_log_dbg("src canvas: addr(%lx),stride(%d),height(%d)", + cfg->src_canvas_cfg[i].phys_addr, + cfg->src_canvas_cfg[i].stride, + cfg->src_canvas_cfg[i].height); + canvas_set = 1; + } + } + if (canvas_set) { + cfg->src1_data.canaddr = index_src; + ge2d_log_dbg("src canvas_index:%x\n", index_src); + canvas_set = 0; + } + for (i = 0; i < MAX_PLANE; i++) { + if (cfg->src2_canvas_cfg[i].canvas_used) { + index_src2 |= index << (8 * i); +#ifdef CONFIG_AMLOGIC_MEDIA_CANVAS + canvas_config(index++, + cfg->src2_canvas_cfg[i].phys_addr, + cfg->src2_canvas_cfg[i].stride, + cfg->src2_canvas_cfg[i].height, + CANVAS_ADDR_NOWRAP, + CANVAS_BLKMODE_LINEAR); +#endif + cfg->src2_canvas_cfg[i].canvas_used = 0; + ge2d_log_dbg("src2 canvas: addr(%lx),stride(%d),height(%d)", + cfg->src2_canvas_cfg[i].phys_addr, + cfg->src2_canvas_cfg[i].stride, + cfg->src2_canvas_cfg[i].height); + canvas_set = 1; + } + } + if (canvas_set) { + cfg->src2_dst_data.src2_canaddr = index_src2; + ge2d_log_dbg("src2 canvas_index:%x\n", index_src2); + canvas_set = 0; + } + + for (i = 0; i < MAX_PLANE; i++) { + if (cfg->dst_canvas_cfg[i].canvas_used) { + index_dst |= index << (8 * i); +#ifdef CONFIG_AMLOGIC_MEDIA_CANVAS + canvas_config(index++, + cfg->dst_canvas_cfg[i].phys_addr, + cfg->dst_canvas_cfg[i].stride, + cfg->dst_canvas_cfg[i].height, + CANVAS_ADDR_NOWRAP, + CANVAS_BLKMODE_LINEAR); +#endif + cfg->dst_canvas_cfg[i].canvas_used = 0; + ge2d_log_dbg("dst canvas: addr(%lx),stride(%d),height(%d)", + cfg->dst_canvas_cfg[i].phys_addr, + cfg->dst_canvas_cfg[i].stride, + cfg->dst_canvas_cfg[i].height); + canvas_set = 1; + } + } + if (canvas_set) { + cfg->src2_dst_data.dst_canaddr = index_dst; + ge2d_log_dbg("dst canvas_index:%x\n", index_dst); + } +} static int ge2d_process_work_queue(struct ge2d_context_s *wq) { struct ge2d_config_s *cfg; @@ -334,6 +414,7 @@ static int ge2d_process_work_queue(struct ge2d_context_s *wq) do { cfg = &pitem->config; + ge2d_set_canvas(cfg); mask = 0x1; while (cfg->update_flag && mask <= UPDATE_SCALE_COEF) { /* we do not change */ @@ -430,6 +511,40 @@ static irqreturn_t ge2d_wq_handle(int irq_number, void *para) return IRQ_HANDLED; } +static void update_canvas_cfg(struct ge2d_canvas_cfg_s *canvas_cfg, + unsigned long phys_addr, + unsigned int stride, + unsigned int height) +{ + canvas_cfg->canvas_used = 1; + canvas_cfg->phys_addr = phys_addr; + canvas_cfg->stride = stride; + canvas_cfg->height = height; +} + +struct ge2d_canvas_cfg_s *ge2d_wq_get_canvas_cfg(struct ge2d_context_s *wq, + unsigned int data_type, + unsigned int plane_id) +{ + struct ge2d_canvas_cfg_s *canvas_cfg = NULL; + + switch (data_type) { + case AML_GE2D_SRC: + canvas_cfg = &wq->config.src_canvas_cfg[plane_id]; + break; + case AML_GE2D_SRC2: + canvas_cfg = &wq->config.src2_canvas_cfg[plane_id]; + break; + case AML_GE2D_DST: + canvas_cfg = &wq->config.dst_canvas_cfg[plane_id]; + break; + default: + ge2d_log_err("wrong data_type\n"); + break; + } + return canvas_cfg; +} + struct ge2d_dma_cfg_s *ge2d_wq_get_dma_cfg(struct ge2d_context_s *wq, unsigned int data_type, unsigned int plane_id) @@ -623,81 +738,45 @@ static inline int bpp(unsigned int format) } } -static void build_ge2d_config(struct config_para_s *cfg, +static int build_ge2d_config(struct ge2d_context_s *context, + struct config_para_s *cfg, struct src_dst_para_s *src, - struct src_dst_para_s *dst, - int index) + struct src_dst_para_s *dst) { - index &= 0xff; + struct ge2d_canvas_cfg_s *canvas_cfg = NULL; + int i; + if (src) { src->xres = cfg->src_planes[0].w; src->yres = cfg->src_planes[0].h; src->ge2d_color_index = cfg->src_format; src->bpp = bpp(cfg->src_format); - if (cfg->src_planes[0].addr) { - if (ge2d_meson_dev.canvas_status == 1) { - src->canvas_index = 0; - src->phy_addr = cfg->src_planes[0].addr; - src->stride = cfg->src_planes[0].w * - src->bpp / 8; + for (i = 0; i < MAX_PLANE; i++) { + if (cfg->src_planes[0].addr) { + if (ge2d_meson_dev.canvas_status == 1) { + if (i == 0) { + src->canvas_index = 0; + src->phy_addr = + cfg->src_planes[0].addr; + src->stride = + cfg->src_planes[0].w * + src->bpp / 8; + } else { + ge2d_log_info("not support src_planes>1\n"); + } + } else { + src->canvas_index = 0; + canvas_cfg = ge2d_wq_get_canvas_cfg + (context, AML_GE2D_SRC, i); + if (!canvas_cfg) + return -1; + update_canvas_cfg(canvas_cfg, + cfg->src_planes[i].addr, + cfg->src_planes[i].w * + src->bpp / 8, + cfg->src_planes[i].h); + } } -#ifdef CONFIG_AMLOGIC_MEDIA_CANVAS - else { - src->canvas_index = index; - canvas_config(index++, - cfg->src_planes[0].addr, - cfg->src_planes[0].w * src->bpp / 8, - cfg->src_planes[0].h, - CANVAS_ADDR_NOWRAP, - CANVAS_BLKMODE_LINEAR); - } -#endif - } - /* multi-src_planes */ - if (cfg->src_planes[1].addr) { - if (ge2d_meson_dev.canvas_status == 1) - ge2d_log_info("ge2d not support src_planes[1]\n"); -#ifdef CONFIG_AMLOGIC_MEDIA_CANVAS - else { - src->canvas_index |= index << 8; - canvas_config(index++, - cfg->src_planes[1].addr, - cfg->src_planes[1].w * src->bpp / 8, - cfg->src_planes[1].h, - CANVAS_ADDR_NOWRAP, - CANVAS_BLKMODE_LINEAR); - } -#endif - } - if (cfg->src_planes[2].addr) { - if (ge2d_meson_dev.canvas_status == 1) - ge2d_log_info("ge2d not support src_planes[2]\n"); -#ifdef CONFIG_AMLOGIC_MEDIA_CANVAS - else { - src->canvas_index |= index << 16; - canvas_config(index++, - cfg->src_planes[2].addr, - cfg->src_planes[2].w * src->bpp / 8, - cfg->src_planes[2].h, - CANVAS_ADDR_NOWRAP, - CANVAS_BLKMODE_LINEAR); - } -#endif - } - if (cfg->src_planes[3].addr) { - if (ge2d_meson_dev.canvas_status == 1) - ge2d_log_info("ge2d not support src_planes[3]\n"); -#ifdef CONFIG_AMLOGIC_MEDIA_CANVAS - else { - src->canvas_index |= index << 24; - canvas_config(index++, - cfg->src_planes[3].addr, - cfg->src_planes[3].w * src->bpp / 8, - cfg->src_planes[3].h, - CANVAS_ADDR_NOWRAP, - CANVAS_BLKMODE_LINEAR); - } -#endif } } if (dst) { @@ -705,72 +784,35 @@ static void build_ge2d_config(struct config_para_s *cfg, dst->yres = cfg->dst_planes[0].h; dst->ge2d_color_index = cfg->dst_format; dst->bpp = bpp(cfg->dst_format); - if (cfg->dst_planes[0].addr) { - if (ge2d_meson_dev.canvas_status == 1) { - dst->canvas_index = 0; - dst->phy_addr = cfg->dst_planes[0].addr; - dst->stride = cfg->dst_planes[0].w * - dst->bpp / 8; + for (i = 0; i < MAX_PLANE; i++) { + if (cfg->dst_planes[i].addr) { + if (ge2d_meson_dev.canvas_status == 1) { + if (i == 0) { + dst->canvas_index = 0; + dst->phy_addr = + cfg->dst_planes[0].addr; + dst->stride = + cfg->dst_planes[0].w * + dst->bpp / 8; + } else { + ge2d_log_info("not support dst_planes>1\n"); + } + } else { + dst->canvas_index = 0; + canvas_cfg = ge2d_wq_get_canvas_cfg + (context, AML_GE2D_DST, i); + if (!canvas_cfg) + return -1; + update_canvas_cfg(canvas_cfg, + cfg->dst_planes[i].addr, + cfg->dst_planes[i].w * + src->bpp / 8, + cfg->dst_planes[i].h); + } } -#ifdef CONFIG_AMLOGIC_MEDIA_CANVAS - else { - dst->canvas_index = index; - canvas_config(index++ & 0xff, - cfg->dst_planes[0].addr, - cfg->dst_planes[0].w, - cfg->dst_planes[0].h, - CANVAS_ADDR_NOWRAP, - CANVAS_BLKMODE_LINEAR); - } -#endif - } - /* multi-src_planes */ - if (cfg->dst_planes[1].addr) { - if (ge2d_meson_dev.canvas_status == 1) - ge2d_log_info("ge2d not support dst_planes[1]\n"); -#ifdef CONFIG_AMLOGIC_MEDIA_CANVAS - else { - dst->canvas_index |= index << 8; - canvas_config(index++, - cfg->dst_planes[1].addr, - cfg->dst_planes[1].w, - cfg->dst_planes[1].h, - CANVAS_ADDR_NOWRAP, - CANVAS_BLKMODE_LINEAR); - } -#endif - } - if (cfg->dst_planes[2].addr) { - if (ge2d_meson_dev.canvas_status == 1) - ge2d_log_info("ge2d not support dst_planes[2]\n"); -#ifdef CONFIG_AMLOGIC_MEDIA_CANVAS - else { - dst->canvas_index |= index << 16; - canvas_config(index++, - cfg->dst_planes[2].addr, - cfg->dst_planes[2].w, - cfg->dst_planes[2].h, - CANVAS_ADDR_NOWRAP, - CANVAS_BLKMODE_LINEAR); - } -#endif - } - if (cfg->dst_planes[3].addr) { - if (ge2d_meson_dev.canvas_status == 1) - ge2d_log_info("ge2d not support dst_planes[3]\n"); -#ifdef CONFIG_AMLOGIC_MEDIA_CANVAS - else { - dst->canvas_index |= index << 24; - canvas_config(index++, - cfg->dst_planes[3].addr, - cfg->dst_planes[3].w, - cfg->dst_planes[3].h, - CANVAS_ADDR_NOWRAP, - CANVAS_BLKMODE_LINEAR); - } -#endif } } + return 0; } static int setup_display_property(struct src_dst_para_s *src_dst, int index) @@ -915,13 +957,13 @@ int ge2d_context_config(struct ge2d_context_s *context, break; case ALLOC_OSD0: dst = src; - build_ge2d_config(ge2d_config, &src, NULL, ALLOC_CANVAS_INDEX); + build_ge2d_config(context, ge2d_config, &src, NULL); break; case ALLOC_OSD1: - build_ge2d_config(ge2d_config, &src, NULL, ALLOC_CANVAS_INDEX); + build_ge2d_config(context, ge2d_config, &src, NULL); break; case ALLOC_ALLOC: - build_ge2d_config(ge2d_config, &src, &dst, ALLOC_CANVAS_INDEX); + build_ge2d_config(context, ge2d_config, &src, &dst); break; } if (src.bpp < 16 || dst.bpp < 16) @@ -1083,86 +1125,52 @@ static int build_ge2d_addr_config_dma( return ret; } -static int build_ge2d_config_ex(struct config_planes_s *plane, +static int build_ge2d_config_ex(struct ge2d_context_s *context, + struct config_planes_s *plane, unsigned int format, - unsigned int *canvas_index, - int index, - unsigned int *r_offset) + unsigned int data_type) { + struct ge2d_canvas_cfg_s *canvas_cfg = NULL; int bpp_value = bpp(format); - int ret = -1; + int ret = -1, i = 0; bpp_value /= 8; - index &= 0xff; if (plane) { - if (plane[0].addr) { - *canvas_index = index; - *r_offset += 1; -#ifdef CONFIG_AMLOGIC_MEDIA_CANVAS - canvas_config(index++, plane[0].addr, - plane[0].w * bpp_value, - plane[0].h, - CANVAS_ADDR_NOWRAP, - CANVAS_BLKMODE_LINEAR); -#endif - ret = 0; - } - /* multi-src_planes */ - if (plane[1].addr) { - *canvas_index |= index << 8; - *r_offset += 1; -#ifdef CONFIG_AMLOGIC_MEDIA_CANVAS - canvas_config(index++, plane[1].addr, - plane[1].w * bpp_value, - plane[1].h, - CANVAS_ADDR_NOWRAP, - CANVAS_BLKMODE_LINEAR); -#endif - } - if (plane[2].addr) { - *canvas_index |= index << 16; - *r_offset += 1; -#ifdef CONFIG_AMLOGIC_MEDIA_CANVAS - canvas_config(index++, plane[2].addr, - plane[2].w * bpp_value, - plane[2].h, - CANVAS_ADDR_NOWRAP, - CANVAS_BLKMODE_LINEAR); -#endif - } - if (plane[3].addr) { - *canvas_index |= index << 24; - *r_offset += 1; -#ifdef CONFIG_AMLOGIC_MEDIA_CANVAS - canvas_config(index++, plane[3].addr, - plane[3].w * bpp_value, - plane[3].h, - CANVAS_ADDR_NOWRAP, - CANVAS_BLKMODE_LINEAR); -#endif + for (i = 0; i < MAX_PLANE; i++) { + if (plane[i].addr) { + canvas_cfg = ge2d_wq_get_canvas_cfg(context, + data_type, i); + if (!canvas_cfg) + return -1; + update_canvas_cfg(canvas_cfg, + plane[i].addr, + plane[i].w * bpp_value, + plane[i].h); + ret = 0; + } } } return ret; } -static int build_ge2d_config_ex_ion(struct config_planes_ion_s *plane, +static int build_ge2d_config_ex_ion(struct ge2d_context_s *context, + struct config_planes_ion_s *plane, unsigned int format, - unsigned int *canvas_index, - int index, - unsigned int *r_offset) + unsigned int data_type) { + struct ge2d_canvas_cfg_s *canvas_cfg = NULL; int bpp_value = bpp(format); int ret = -1, i; + int canvas_set = 0; unsigned long addr; size_t len; bpp_value /= 8; - index &= 0xff; - *canvas_index = 0; if (plane) { for (i = 0; i < MAX_PLANE; i++) { /* multi-src_planes */ + canvas_set = 0; if (plane[i].shared_fd) { #ifdef CONFIG_AMLOGIC_ION ret = meson_ion_share_fd_to_phys(ge2d_ion_client, @@ -1173,52 +1181,45 @@ static int build_ge2d_config_ex_ion(struct config_planes_ion_s *plane, return ret; #endif plane[i].addr = addr; - *canvas_index |= index << (8 * i); - *r_offset += 1; -#ifdef CONFIG_AMLOGIC_MEDIA_CANVAS - canvas_config(index++, plane[i].addr, - plane[i].w * bpp_value, - plane[i].h, - CANVAS_ADDR_NOWRAP, - CANVAS_BLKMODE_LINEAR); -#endif - ret = 0; + canvas_set = 1; } else if (plane[i].addr) { plane[i].addr += plane[0].addr; - *canvas_index |= index << (8 * i); - *r_offset += 1; -#ifdef CONFIG_AMLOGIC_MEDIA_CANVAS - canvas_config(index++, plane[i].addr, + canvas_set = 1; + } + if (canvas_set) { + canvas_cfg = ge2d_wq_get_canvas_cfg(context, + data_type, i); + if (!canvas_cfg) + return -1; + update_canvas_cfg(canvas_cfg, + plane[i].addr, plane[i].w * bpp_value, - plane[i].h, - CANVAS_ADDR_NOWRAP, - CANVAS_BLKMODE_LINEAR); -#endif + plane[i].h); + canvas_set = 0; ret = 0; } } } return ret; } + static int build_ge2d_config_ex_dma(struct ge2d_context_s *context, struct config_planes_ion_s *plane, unsigned int format, - unsigned int *canvas_index, - int index, - unsigned int *r_offset, unsigned int dir, unsigned int data_type) { + struct ge2d_canvas_cfg_s *canvas_cfg = NULL; int bpp_value = bpp(format); int ret = -1, i; + int canvas_set = 0; unsigned long addr; bpp_value /= 8; - index &= 0xff; - *canvas_index = 0; if (plane) { for (i = 0; i < MAX_PLANE; i++) { /* multi-src_planes */ + canvas_set = 0; if (plane[i].shared_fd) { struct ge2d_dma_cfg_s *cfg = NULL; struct aml_dma_cfg *dma_cfg = NULL; @@ -1239,26 +1240,21 @@ static int build_ge2d_config_ex_dma(struct ge2d_context_s *context, if (ret != 0) return ret; plane[i].addr = addr; - *canvas_index |= index << (8 * i); - *r_offset += 1; -#ifdef CONFIG_AMLOGIC_MEDIA_CANVAS - canvas_config(index++, plane[i].addr, - plane[i].w * bpp_value, - plane[i].h, - CANVAS_ADDR_NOWRAP, - CANVAS_BLKMODE_LINEAR); -#endif + canvas_set = 1; } else if (plane[i].addr) { plane[i].addr += plane[0].addr; - *canvas_index |= index << (8 * i); - *r_offset += 1; -#ifdef CONFIG_AMLOGIC_MEDIA_CANVAS - canvas_config(index++, plane[i].addr, - plane[i].w * bpp_value, - plane[i].h, - CANVAS_ADDR_NOWRAP, - CANVAS_BLKMODE_LINEAR); -#endif + canvas_set = 1; + } + if (canvas_set) { + canvas_cfg = ge2d_wq_get_canvas_cfg(context, + data_type, i); + if (!canvas_cfg) + return -1; + update_canvas_cfg(canvas_cfg, + plane[i].addr, + plane[i].w * bpp_value, + plane[i].h); + canvas_set = 0; } } } @@ -1269,8 +1265,6 @@ int ge2d_context_config_ex(struct ge2d_context_s *context, struct config_para_ex_s *ge2d_config) { struct src_dst_para_s tmp; - unsigned int index = 0; - unsigned int alloc_canvas_offset = 0; struct ge2d_src1_gen_s *src1_gen_cfg; struct ge2d_src2_dst_data_s *src2_dst_data_cfg; struct ge2d_src2_dst_gen_s *src2_dst_gen_cfg; @@ -1334,15 +1328,14 @@ int ge2d_context_config_ex(struct ge2d_context_s *context, src_stride, ge2d_config->src_para.format); } else { - if (build_ge2d_config_ex(&ge2d_config->src_planes[0], + if (build_ge2d_config_ex(context, + &ge2d_config->src_planes[0], ge2d_config->src_para.format, - &index, - ALLOC_CANVAS_INDEX + alloc_canvas_offset, - &alloc_canvas_offset) < 0) + AML_GE2D_SRC) < 0) return -1; - ge2d_config->src_para.canvas_index = index; - ge2d_log_dbg("ge2d alloc canvas index:0x%x, format:0x%x\n", - index, ge2d_config->src_para.format); + ge2d_config->src_para.canvas_index = 0; + ge2d_log_dbg("ge2d src alloc,format:0x%x\n", + ge2d_config->src_para.format); } break; default: @@ -1409,17 +1402,14 @@ int ge2d_context_config_ex(struct ge2d_context_s *context, src2_stride, ge2d_config->src2_para.format); } else { - if (build_ge2d_config_ex( + if (build_ge2d_config_ex(context, &ge2d_config->src2_planes[0], ge2d_config->src2_para.format, - &index, - ALLOC_CANVAS_INDEX + - alloc_canvas_offset, - &alloc_canvas_offset) < 0) + AML_GE2D_SRC2) < 0) return -1; - ge2d_config->src2_para.canvas_index = index; - ge2d_log_dbg("ge2d src2 alloc, canvas index:0x%x,format:0x%x\n", - index, ge2d_config->src2_para.format); + ge2d_config->src2_para.canvas_index = 0; + ge2d_log_dbg("ge2d src2 alloc,format:0x%x\n", + ge2d_config->src2_para.format); } } break; @@ -1495,17 +1485,14 @@ int ge2d_context_config_ex(struct ge2d_context_s *context, dst_stride, ge2d_config->dst_para.format); } else { - if (build_ge2d_config_ex( + if (build_ge2d_config_ex(context, &ge2d_config->dst_planes[0], ge2d_config->dst_para.format, - &index, - ALLOC_CANVAS_INDEX + - alloc_canvas_offset, - &alloc_canvas_offset) < 0) + AML_GE2D_DST) < 0) return -1; - ge2d_config->dst_para.canvas_index = index; - ge2d_log_dbg("ge2d: dst alloc, index:0x%x, format:0x%x\n", - index, ge2d_config->dst_para.format); + ge2d_config->dst_para.canvas_index = 0; + ge2d_log_dbg("ge2d: dst alloc,format:0x%x\n", + ge2d_config->dst_para.format); } } break; @@ -1647,8 +1634,6 @@ int ge2d_context_config_ex_ion(struct ge2d_context_s *context, struct config_para_ex_ion_s *ge2d_config) { struct src_dst_para_s tmp; - unsigned int index = 0; - unsigned int alloc_canvas_offset = 0; struct ge2d_src1_gen_s *src1_gen_cfg; struct ge2d_src2_dst_data_s *src2_dst_data_cfg; struct ge2d_src2_dst_gen_s *src2_dst_gen_cfg; @@ -1715,15 +1700,14 @@ int ge2d_context_config_ex_ion(struct ge2d_context_s *context, } else { if (build_ge2d_config_ex_ion( + context, &ge2d_config->src_planes[0], ge2d_config->src_para.format, - &index, - ALLOC_CANVAS_INDEX + alloc_canvas_offset, - &alloc_canvas_offset) < 0) + AML_GE2D_SRC) < 0) return -1; - ge2d_config->src_para.canvas_index = index; - ge2d_log_dbg("ge2d alloc canvas index:0x%x, format:0x%x\n", - index, ge2d_config->src_para.format); + ge2d_config->src_para.canvas_index = 0; + ge2d_log_dbg("ge2d src alloc,format:0x%x\n", + ge2d_config->src_para.format); } break; default: @@ -1790,15 +1774,14 @@ int ge2d_context_config_ex_ion(struct ge2d_context_s *context, ge2d_config->src2_para.format); } else { if (build_ge2d_config_ex_ion( + context, &ge2d_config->src2_planes[0], ge2d_config->src2_para.format, - &index, - ALLOC_CANVAS_INDEX + alloc_canvas_offset, - &alloc_canvas_offset) < 0) + AML_GE2D_SRC2) < 0) return -1; - ge2d_config->src2_para.canvas_index = index; - ge2d_log_dbg("ge2d src2 alloc, canvas index:0x%x,format:0x%x\n", - index, ge2d_config->src2_para.format); + ge2d_config->src2_para.canvas_index = 0; + ge2d_log_dbg("ge2d src2 alloc,format:0x%x\n", + ge2d_config->src2_para.format); } break; default: @@ -1868,15 +1851,14 @@ int ge2d_context_config_ex_ion(struct ge2d_context_s *context, ge2d_config->dst_para.format); } else { if (build_ge2d_config_ex_ion( + context, &ge2d_config->dst_planes[0], ge2d_config->dst_para.format, - &index, - ALLOC_CANVAS_INDEX + alloc_canvas_offset, - &alloc_canvas_offset) < 0) + AML_GE2D_DST) < 0) return -1; - ge2d_config->dst_para.canvas_index = index; - ge2d_log_dbg("ge2d: dst alloc, index:0x%x, format:0x%x\n", - index, ge2d_config->dst_para.format); + ge2d_config->dst_para.canvas_index = 0; + ge2d_log_dbg("ge2d: dst alloc,format:0x%x\n", + ge2d_config->dst_para.format); } break; default: @@ -2022,8 +2004,6 @@ int ge2d_context_config_ex_mem(struct ge2d_context_s *context, struct config_para_ex_memtype_s *ge2d_config_mem) { struct src_dst_para_s tmp; - unsigned int index = 0; - unsigned int alloc_canvas_offset = 0; struct ge2d_src1_gen_s *src1_gen_cfg; struct ge2d_src2_dst_data_s *src2_dst_data_cfg; struct ge2d_src2_dst_gen_s *src2_dst_gen_cfg; @@ -2118,32 +2098,26 @@ int ge2d_context_config_ex_mem(struct ge2d_context_s *context, if (ge2d_config_mem->src1_mem_alloc_type == AML_GE2D_MEM_ION) { if (build_ge2d_config_ex_ion( + context, &ge2d_config->src_planes[0], ge2d_config->src_para.format, - &index, - ALLOC_CANVAS_INDEX + - alloc_canvas_offset, - &alloc_canvas_offset) < 0) + AML_GE2D_SRC) < 0) return -1; - ge2d_config->src_para.canvas_index = index; - ge2d_log_dbg("ge2d ion alloc canvas index:0x%x, format:0x%x\n", - index, ge2d_config->src_para.format); + ge2d_config->src_para.canvas_index = 0; + ge2d_log_dbg("ge2d ion alloc,format:0x%x\n", + ge2d_config->src_para.format); } else if (ge2d_config_mem->src1_mem_alloc_type == AML_GE2D_MEM_DMABUF) { if (build_ge2d_config_ex_dma( context, &ge2d_config->src_planes[0], ge2d_config->src_para.format, - &index, - ALLOC_CANVAS_INDEX + - alloc_canvas_offset, - &alloc_canvas_offset, DMA_TO_DEVICE, AML_GE2D_SRC) < 0) return -1; - ge2d_config->src_para.canvas_index = index; - ge2d_log_dbg("ge2d dma alloc canvas index:0x%x, format:0x%x\n", - index, ge2d_config->src_para.format); + ge2d_config->src_para.canvas_index = 0; + ge2d_log_dbg("ge2d dma alloc,format:0x%x\n", + ge2d_config->src_para.format); } } break; @@ -2231,32 +2205,26 @@ int ge2d_context_config_ex_mem(struct ge2d_context_s *context, if (ge2d_config_mem->src2_mem_alloc_type == AML_GE2D_MEM_ION) { if (build_ge2d_config_ex_ion( + context, &ge2d_config->src2_planes[0], ge2d_config->src2_para.format, - &index, - ALLOC_CANVAS_INDEX + - alloc_canvas_offset, - &alloc_canvas_offset) < 0) + AML_GE2D_SRC2) < 0) return -1; - ge2d_config->src2_para.canvas_index = index; - ge2d_log_dbg("ge2d src2 ion alloc, canvas index:0x%x,format:0x%x\n", - index, ge2d_config->src2_para.format); + ge2d_config->src2_para.canvas_index = 0; + ge2d_log_dbg("ge2d src2 ion alloc,format:0x%x\n", + ge2d_config->src2_para.format); } else if (ge2d_config_mem->src2_mem_alloc_type == AML_GE2D_MEM_DMABUF) { if (build_ge2d_config_ex_dma( context, &ge2d_config->src2_planes[0], ge2d_config->src2_para.format, - &index, - ALLOC_CANVAS_INDEX + - alloc_canvas_offset, - &alloc_canvas_offset, DMA_TO_DEVICE, AML_GE2D_SRC2) < 0) return -1; - ge2d_config->src2_para.canvas_index = index; - ge2d_log_dbg("ge2d src2 dma alloc, canvas index:0x%x,format:0x%x\n", - index, ge2d_config->src2_para.format); + ge2d_config->src2_para.canvas_index = 0; + ge2d_log_dbg("ge2d src2 dma alloc,format:0x%x\n", + ge2d_config->src2_para.format); } } break; @@ -2347,32 +2315,26 @@ int ge2d_context_config_ex_mem(struct ge2d_context_s *context, if (ge2d_config_mem->dst_mem_alloc_type == AML_GE2D_MEM_ION) { if (build_ge2d_config_ex_ion( + context, &ge2d_config->dst_planes[0], ge2d_config->dst_para.format, - &index, - ALLOC_CANVAS_INDEX + - alloc_canvas_offset, - &alloc_canvas_offset) < 0) + AML_GE2D_DST) < 0) return -1; - ge2d_config->dst_para.canvas_index = index; - ge2d_log_dbg("ge2d: dst ion alloc, index:0x%x, format:0x%x\n", - index, ge2d_config->dst_para.format); + ge2d_config->dst_para.canvas_index = 0; + ge2d_log_dbg("ge2d: dst ion alloc,format:0x%x\n", + ge2d_config->dst_para.format); } else if (ge2d_config_mem->dst_mem_alloc_type == AML_GE2D_MEM_DMABUF) { if (build_ge2d_config_ex_dma( context, &ge2d_config->dst_planes[0], ge2d_config->dst_para.format, - &index, - ALLOC_CANVAS_INDEX + - alloc_canvas_offset, - &alloc_canvas_offset, DMA_FROM_DEVICE, AML_GE2D_DST) < 0) return -1; - ge2d_config->dst_para.canvas_index = index; - ge2d_log_dbg("ge2d: dst dma alloc, index:0x%x, format:0x%x\n", - index, ge2d_config->dst_para.format); + ge2d_config->dst_para.canvas_index = 0; + ge2d_log_dbg("ge2d: dst dma alloc,format:0x%x\n", + ge2d_config->dst_para.format); } } break; diff --git a/drivers/amlogic/media/gdc/app/gdc_dmabuf.c b/drivers/amlogic/media/gdc/app/gdc_dmabuf.c index 6d7016596cbe..216a09e7f40f 100644 --- a/drivers/amlogic/media/gdc/app/gdc_dmabuf.c +++ b/drivers/amlogic/media/gdc/app/gdc_dmabuf.c @@ -460,6 +460,7 @@ int gdc_dma_buffer_export(struct aml_dma_buffer *buffer, gdc_log(LOG_INFO, "buffer %d,exported as %d descriptor\n", index, ret); buffer->gd_buffer[index].fd = ret; + buffer->gd_buffer[index].dbuf = dbuf; gdc_exp_buf->fd = ret; return 0; } @@ -534,18 +535,28 @@ attach_err: } static int gdc_dma_buffer_get_phys_internal(struct aml_dma_buffer *buffer, - int fd, unsigned long *addr) + struct aml_dma_cfg *cfg, unsigned long *addr) { int i = 0, ret = -1; struct aml_dma_buf *dma_buf; + struct dma_buf *dbuf = NULL; for (i = 0; i < AML_MAX_DMABUF; i++) { - if (buffer->gd_buffer[i].alloc && - (fd == buffer->gd_buffer[i].fd)) { - dma_buf = buffer->gd_buffer[i].mem_priv; - *addr = dma_buf->dma_addr; - ret = 0; - break; + if (buffer->gd_buffer[i].alloc) { + dbuf = dma_buf_get(cfg->fd); + if (IS_ERR(dbuf)) { + pr_err("%s: failed to get dma buffer,fd=%d, dbuf=%p\n", + __func__, cfg->fd, dbuf); + return -EINVAL; + } + dma_buf_put(dbuf); + if (dbuf == buffer->gd_buffer[i].dbuf) { + cfg->dbuf = dbuf; + dma_buf = buffer->gd_buffer[i].mem_priv; + *addr = dma_buf->dma_addr; + ret = 0; + break; + } } } return ret; @@ -561,7 +572,7 @@ int gdc_dma_buffer_get_phys(struct aml_dma_buffer *buffer, pr_err("error input param"); return -EINVAL; } - ret = gdc_dma_buffer_get_phys_internal(buffer, cfg->fd, addr); + ret = gdc_dma_buffer_get_phys_internal(buffer, cfg, addr); if (ret < 0) { gdc_log(LOG_INFO, "get_phys(fd=%d) failed.\n", cfg->fd); ret = gdc_dma_buffer_map(cfg); @@ -589,10 +600,11 @@ int gdc_dma_buffer_unmap_info(struct aml_dma_buffer *buffer, } for (i = 0; i < AML_MAX_DMABUF; i++) { - if (buffer->gd_buffer[i].alloc && - (cfg->fd == buffer->gd_buffer[i].fd)) { - found = 1; - break; + if (buffer->gd_buffer[i].alloc) { + if (cfg->dbuf == buffer->gd_buffer[i].dbuf) { + found = 1; + break; + } } } if (!found) diff --git a/include/linux/amlogic/media/ge2d/ge2d.h b/include/linux/amlogic/media/ge2d/ge2d.h index ec9e6d0b6dd1..b122fcf075d6 100644 --- a/include/linux/amlogic/media/ge2d/ge2d.h +++ b/include/linux/amlogic/media/ge2d/ge2d.h @@ -616,6 +616,14 @@ struct ge2d_cmd_s { unsigned char hang_flag; }; +struct ge2d_canvas_cfg_s { + int canvas_used; + int canvas_index; + unsigned int stride; + unsigned int height; + unsigned long phys_addr; +}; + struct ge2d_dma_cfg_s { int dma_used; void *dma_cfg; @@ -631,6 +639,9 @@ struct ge2d_config_s { unsigned int v_scale_coef_type; unsigned int h_scale_coef_type; unsigned int update_flag; + struct ge2d_canvas_cfg_s src_canvas_cfg[MAX_PLANE]; + struct ge2d_canvas_cfg_s src2_canvas_cfg[MAX_PLANE]; + struct ge2d_canvas_cfg_s dst_canvas_cfg[MAX_PLANE]; struct ge2d_dma_cfg_s src_dma_cfg[MAX_PLANE]; struct ge2d_dma_cfg_s src2_dma_cfg[MAX_PLANE]; struct ge2d_dma_cfg_s dst_dma_cfg[MAX_PLANE];