diff --git a/driver/vidc/inc/msm_vidc_core.h b/driver/vidc/inc/msm_vidc_core.h index e4c3e826ac..567558c2a4 100644 --- a/driver/vidc/inc/msm_vidc_core.h +++ b/driver/vidc/inc/msm_vidc_core.h @@ -42,8 +42,7 @@ struct msm_vidc_mem_addr { u32 align_device_addr; u8 *align_virtual_addr; u32 mem_size; - struct msm_vidc_map map; - struct msm_vidc_alloc alloc; + struct msm_vidc_mem mem; }; struct msm_vidc_iface_q_info { diff --git a/driver/vidc/inc/msm_vidc_driver.h b/driver/vidc/inc/msm_vidc_driver.h index 83c2bcdc1b..87e9728a2b 100644 --- a/driver/vidc/inc/msm_vidc_driver.h +++ b/driver/vidc/inc/msm_vidc_driver.h @@ -474,9 +474,7 @@ int msm_vidc_vb2_queue_deinit(struct msm_vidc_inst *inst); int msm_vidc_get_control(struct msm_vidc_inst *inst, struct v4l2_ctrl *ctrl); struct msm_vidc_buffers *msm_vidc_get_buffers(struct msm_vidc_inst *inst, enum msm_vidc_buffer_type buffer_type, const char *func); -struct msm_vidc_mappings *msm_vidc_get_mappings(struct msm_vidc_inst *inst, - enum msm_vidc_buffer_type buffer_type, const char *func); -struct msm_vidc_allocations *msm_vidc_get_allocations( +struct msm_vidc_mem_list *msm_vidc_get_mem_info( struct msm_vidc_inst *inst, enum msm_vidc_buffer_type buffer_type, const char *func); struct msm_vidc_buffer *msm_vidc_get_driver_buf(struct msm_vidc_inst *inst, diff --git a/driver/vidc/inc/msm_vidc_inst.h b/driver/vidc/inc/msm_vidc_inst.h index 6196871220..a6cfb049fa 100644 --- a/driver/vidc/inc/msm_vidc_inst.h +++ b/driver/vidc/inc/msm_vidc_inst.h @@ -39,28 +39,16 @@ struct msm_vidc_session_ops { int (*extra_count)(struct msm_vidc_inst *inst, enum msm_vidc_buffer_type type); }; -struct msm_vidc_allocations_info { - struct msm_vidc_allocations bin; - struct msm_vidc_allocations arp; - struct msm_vidc_allocations comv; - struct msm_vidc_allocations non_comv; - struct msm_vidc_allocations line; - struct msm_vidc_allocations dpb; - struct msm_vidc_allocations persist; - struct msm_vidc_allocations vpss; - struct msm_vidc_allocations partial_data; -}; - -struct msm_vidc_mappings_info { - struct msm_vidc_mappings bin; - struct msm_vidc_mappings arp; - struct msm_vidc_mappings comv; - struct msm_vidc_mappings non_comv; - struct msm_vidc_mappings line; - struct msm_vidc_mappings dpb; - struct msm_vidc_mappings persist; - struct msm_vidc_mappings vpss; - struct msm_vidc_mappings partial_data; +struct msm_vidc_mem_list_info { + struct msm_vidc_mem_list bin; + struct msm_vidc_mem_list arp; + struct msm_vidc_mem_list comv; + struct msm_vidc_mem_list non_comv; + struct msm_vidc_mem_list line; + struct msm_vidc_mem_list dpb; + struct msm_vidc_mem_list persist; + struct msm_vidc_mem_list vpss; + struct msm_vidc_mem_list partial_data; }; struct msm_vidc_buffers_info { @@ -136,8 +124,7 @@ struct msm_vidc_inst { struct vidc_bus_vote_data bus_data; struct msm_memory_pool pool[MSM_MEM_POOL_MAX]; struct msm_vidc_buffers_info buffers; - struct msm_vidc_mappings_info mappings; - struct msm_vidc_allocations_info allocations; + struct msm_vidc_mem_list_info mem_info; struct msm_vidc_timestamps timestamps; struct msm_vidc_timestamps ts_reorder; /* list of struct msm_vidc_timestamp */ bool subscribed_input_psc; diff --git a/driver/vidc/inc/msm_vidc_internal.h b/driver/vidc/inc/msm_vidc_internal.h index 0e250c7a06..c98a5b15dd 100644 --- a/driver/vidc/inc/msm_vidc_internal.h +++ b/driver/vidc/inc/msm_vidc_internal.h @@ -836,7 +836,7 @@ struct msm_vidc_fence { int fd; }; -struct msm_vidc_alloc { +struct msm_vidc_mem { struct list_head list; enum msm_vidc_buffer_type type; enum msm_vidc_buffer_region region; @@ -854,25 +854,15 @@ struct msm_vidc_alloc { struct dma_buf_map dmabuf_map; #endif void *kvaddr; -}; - -struct msm_vidc_allocations { - struct list_head list; // list of "struct msm_vidc_alloc" -}; - -struct msm_vidc_map { - struct list_head list; - enum msm_vidc_buffer_type type; - enum msm_vidc_buffer_region region; - struct dma_buf *dmabuf; + dma_addr_t device_addr; + unsigned long attrs; u32 refcount; - u64 device_addr; struct sg_table *table; struct dma_buf_attachment *attach; }; -struct msm_vidc_mappings { - struct list_head list; // list of "struct msm_vidc_map" +struct msm_vidc_mem_list { + struct list_head list; // list of "struct msm_vidc_mem" }; struct msm_vidc_buffer { diff --git a/driver/vidc/inc/msm_vidc_memory.h b/driver/vidc/inc/msm_vidc_memory.h index 3e0e643004..0f908c8361 100644 --- a/driver/vidc/inc/msm_vidc_memory.h +++ b/driver/vidc/inc/msm_vidc_memory.h @@ -21,8 +21,7 @@ struct msm_memory_dmabuf { enum msm_memory_pool_type { MSM_MEM_POOL_BUFFER = 0, - MSM_MEM_POOL_MAP, - MSM_MEM_POOL_ALLOC, + MSM_MEM_POOL_ALLOC_MAP, MSM_MEM_POOL_TIMESTAMP, MSM_MEM_POOL_DMABUF, MSM_MEM_POOL_PACKET, @@ -72,14 +71,10 @@ struct msm_vidc_memory_ops { struct dma_buf_attachment *attach); int (*dma_buf_unmap_attachment)(struct msm_vidc_core *core, struct dma_buf_attachment *attach, struct sg_table *table); - int (*memory_map)(struct msm_vidc_core *core, - struct msm_vidc_map *map); - int (*memory_unmap)(struct msm_vidc_core *core, - struct msm_vidc_map *map); - int (*memory_alloc)(struct msm_vidc_core *core, - struct msm_vidc_alloc *alloc); - int (*memory_free)(struct msm_vidc_core *core, - struct msm_vidc_alloc *alloc); + int (*memory_alloc_map)(struct msm_vidc_core *core, + struct msm_vidc_mem *mem); + int (*memory_unmap_free)(struct msm_vidc_core *core, + struct msm_vidc_mem *mem); u32 (*buffer_region)(struct msm_vidc_inst *inst, enum msm_vidc_buffer_type buffer_type); }; diff --git a/driver/vidc/src/msm_vidc.c b/driver/vidc/src/msm_vidc.c index aa152d55bb..c510659a5c 100644 --- a/driver/vidc/src/msm_vidc.c +++ b/driver/vidc/src/msm_vidc.c @@ -934,24 +934,15 @@ void *msm_vidc_open(void *vidc_core, u32 session_type) INIT_LIST_HEAD(&inst->buffers.persist.list); INIT_LIST_HEAD(&inst->buffers.vpss.list); INIT_LIST_HEAD(&inst->buffers.partial_data.list); - INIT_LIST_HEAD(&inst->allocations.bin.list); - INIT_LIST_HEAD(&inst->allocations.arp.list); - INIT_LIST_HEAD(&inst->allocations.comv.list); - INIT_LIST_HEAD(&inst->allocations.non_comv.list); - INIT_LIST_HEAD(&inst->allocations.line.list); - INIT_LIST_HEAD(&inst->allocations.dpb.list); - INIT_LIST_HEAD(&inst->allocations.persist.list); - INIT_LIST_HEAD(&inst->allocations.vpss.list); - INIT_LIST_HEAD(&inst->allocations.partial_data.list); - INIT_LIST_HEAD(&inst->mappings.bin.list); - INIT_LIST_HEAD(&inst->mappings.arp.list); - INIT_LIST_HEAD(&inst->mappings.comv.list); - INIT_LIST_HEAD(&inst->mappings.non_comv.list); - INIT_LIST_HEAD(&inst->mappings.line.list); - INIT_LIST_HEAD(&inst->mappings.dpb.list); - INIT_LIST_HEAD(&inst->mappings.persist.list); - INIT_LIST_HEAD(&inst->mappings.vpss.list); - INIT_LIST_HEAD(&inst->mappings.partial_data.list); + INIT_LIST_HEAD(&inst->mem_info.bin.list); + INIT_LIST_HEAD(&inst->mem_info.arp.list); + INIT_LIST_HEAD(&inst->mem_info.comv.list); + INIT_LIST_HEAD(&inst->mem_info.non_comv.list); + INIT_LIST_HEAD(&inst->mem_info.line.list); + INIT_LIST_HEAD(&inst->mem_info.dpb.list); + INIT_LIST_HEAD(&inst->mem_info.persist.list); + INIT_LIST_HEAD(&inst->mem_info.vpss.list); + INIT_LIST_HEAD(&inst->mem_info.partial_data.list); INIT_LIST_HEAD(&inst->children_list); INIT_LIST_HEAD(&inst->firmware_list); INIT_LIST_HEAD(&inst->enc_input_crs); diff --git a/driver/vidc/src/msm_vidc_driver.c b/driver/vidc/src/msm_vidc_driver.c index def57702a8..493e6f9a75 100644 --- a/driver/vidc/src/msm_vidc_driver.c +++ b/driver/vidc/src/msm_vidc_driver.c @@ -905,59 +905,29 @@ struct msm_vidc_buffers *msm_vidc_get_buffers( } } -struct msm_vidc_mappings *msm_vidc_get_mappings( +struct msm_vidc_mem_list *msm_vidc_get_mem_info( struct msm_vidc_inst *inst, enum msm_vidc_buffer_type buffer_type, const char *func) { switch (buffer_type) { case MSM_VIDC_BUF_BIN: - return &inst->mappings.bin; + return &inst->mem_info.bin; case MSM_VIDC_BUF_ARP: - return &inst->mappings.arp; + return &inst->mem_info.arp; case MSM_VIDC_BUF_COMV: - return &inst->mappings.comv; + return &inst->mem_info.comv; case MSM_VIDC_BUF_NON_COMV: - return &inst->mappings.non_comv; + return &inst->mem_info.non_comv; case MSM_VIDC_BUF_LINE: - return &inst->mappings.line; + return &inst->mem_info.line; case MSM_VIDC_BUF_DPB: - return &inst->mappings.dpb; + return &inst->mem_info.dpb; case MSM_VIDC_BUF_PERSIST: - return &inst->mappings.persist; + return &inst->mem_info.persist; case MSM_VIDC_BUF_VPSS: - return &inst->mappings.vpss; + return &inst->mem_info.vpss; case MSM_VIDC_BUF_PARTIAL_DATA: - return &inst->mappings.partial_data; - default: - i_vpr_e(inst, "%s: invalid driver buffer type %d\n", - func, buffer_type); - return NULL; - } -} - -struct msm_vidc_allocations *msm_vidc_get_allocations( - struct msm_vidc_inst *inst, enum msm_vidc_buffer_type buffer_type, - const char *func) -{ - switch (buffer_type) { - case MSM_VIDC_BUF_BIN: - return &inst->allocations.bin; - case MSM_VIDC_BUF_ARP: - return &inst->allocations.arp; - case MSM_VIDC_BUF_COMV: - return &inst->allocations.comv; - case MSM_VIDC_BUF_NON_COMV: - return &inst->allocations.non_comv; - case MSM_VIDC_BUF_LINE: - return &inst->allocations.line; - case MSM_VIDC_BUF_DPB: - return &inst->allocations.dpb; - case MSM_VIDC_BUF_PERSIST: - return &inst->allocations.persist; - case MSM_VIDC_BUF_VPSS: - return &inst->allocations.vpss; - case MSM_VIDC_BUF_PARTIAL_DATA: - return &inst->allocations.partial_data; + return &inst->mem_info.partial_data; default: i_vpr_e(inst, "%s: invalid driver buffer type %d\n", func, buffer_type); @@ -3496,10 +3466,8 @@ int msm_vidc_destroy_internal_buffer(struct msm_vidc_inst *inst, struct msm_vidc_buffer *buffer) { struct msm_vidc_buffers *buffers; - struct msm_vidc_allocations *allocations; - struct msm_vidc_mappings *mappings; - struct msm_vidc_alloc *alloc, *alloc_dummy; - struct msm_vidc_map *map, *map_dummy; + struct msm_vidc_mem_list *mem_list; + struct msm_vidc_mem *mem, *mem_dummy; struct msm_vidc_buffer *buf, *dummy; struct msm_vidc_core *core; @@ -3521,27 +3489,15 @@ int msm_vidc_destroy_internal_buffer(struct msm_vidc_inst *inst, buffers = msm_vidc_get_buffers(inst, buffer->type, __func__); if (!buffers) return -EINVAL; - allocations = msm_vidc_get_allocations(inst, buffer->type, __func__); - if (!allocations) - return -EINVAL; - mappings = msm_vidc_get_mappings(inst, buffer->type, __func__); - if (!mappings) + mem_list = msm_vidc_get_mem_info(inst, buffer->type, __func__); + if (!mem_list) return -EINVAL; - list_for_each_entry_safe(map, map_dummy, &mappings->list, list) { - if (map->dmabuf == buffer->dmabuf) { - call_mem_op(core, memory_unmap, core, map); - list_del(&map->list); - msm_vidc_pool_free(inst, map); - break; - } - } - - list_for_each_entry_safe(alloc, alloc_dummy, &allocations->list, list) { - if (alloc->dmabuf == buffer->dmabuf) { - call_mem_op(core, memory_free, core, alloc); - list_del(&alloc->list); - msm_vidc_pool_free(inst, alloc); + list_for_each_entry_safe(mem, mem_dummy, &mem_list->list, list) { + if (mem->dmabuf == buffer->dmabuf) { + call_mem_op(core, memory_unmap_free, core, mem); + list_del(&mem->list); + msm_vidc_pool_free(inst, mem); break; } } @@ -3600,11 +3556,9 @@ int msm_vidc_create_internal_buffer(struct msm_vidc_inst *inst, { int rc = 0; struct msm_vidc_buffers *buffers; - struct msm_vidc_allocations *allocations; - struct msm_vidc_mappings *mappings; + struct msm_vidc_mem_list *mem_list; struct msm_vidc_buffer *buffer; - struct msm_vidc_alloc *alloc; - struct msm_vidc_map *map; + struct msm_vidc_mem *mem; struct msm_vidc_core *core; if (!inst || !inst->core) { @@ -3621,11 +3575,8 @@ int msm_vidc_create_internal_buffer(struct msm_vidc_inst *inst, buffers = msm_vidc_get_buffers(inst, buffer_type, __func__); if (!buffers) return -EINVAL; - allocations = msm_vidc_get_allocations(inst, buffer_type, __func__); - if (!allocations) - return -EINVAL; - mappings = msm_vidc_get_mappings(inst, buffer_type, __func__); - if (!mappings) + mem_list = msm_vidc_get_mem_info(inst, buffer_type, __func__); + if (!mem_list) return -EINVAL; if (!buffers->size) @@ -3642,37 +3593,23 @@ int msm_vidc_create_internal_buffer(struct msm_vidc_inst *inst, buffer->buffer_size = buffers->size; list_add_tail(&buffer->list, &buffers->list); - alloc = msm_vidc_pool_alloc(inst, MSM_MEM_POOL_ALLOC); - if (!alloc) { - i_vpr_e(inst, "%s: alloc failed\n", __func__); + mem = msm_vidc_pool_alloc(inst, MSM_MEM_POOL_ALLOC_MAP); + if (!mem) { + i_vpr_e(inst, "%s: mem poo alloc failed\n", __func__); return -ENOMEM; } - INIT_LIST_HEAD(&alloc->list); - alloc->type = buffer_type; - alloc->region = call_mem_op(core, buffer_region, inst, buffer_type); - alloc->size = buffer->buffer_size; - alloc->secure = is_secure_region(alloc->region); - rc = call_mem_op(core, memory_alloc, core, alloc); + INIT_LIST_HEAD(&mem->list); + mem->type = buffer_type; + mem->region = call_mem_op(core, buffer_region, inst, buffer_type); + mem->size = buffer->buffer_size; + mem->secure = is_secure_region(mem->region); + rc = call_mem_op(core, memory_alloc_map, core, mem); if (rc) return -ENOMEM; - list_add_tail(&alloc->list, &allocations->list); + list_add_tail(&mem->list, &mem_list->list); - map = msm_vidc_pool_alloc(inst, MSM_MEM_POOL_MAP); - if (!map) { - i_vpr_e(inst, "%s: map alloc failed\n", __func__); - return -ENOMEM; - } - INIT_LIST_HEAD(&map->list); - map->type = alloc->type; - map->region = alloc->region; - map->dmabuf = alloc->dmabuf; - rc = call_mem_op(core, memory_map, core, map); - if (rc) - return -ENOMEM; - list_add_tail(&map->list, &mappings->list); - - buffer->dmabuf = alloc->dmabuf; - buffer->device_addr = map->device_addr; + buffer->dmabuf = mem->dmabuf; + buffer->device_addr = mem->device_addr; i_vpr_h(inst, "%s: create: type: %8s, size: %9u, device_addr %#llx\n", __func__, buf_name(buffer_type), buffers->size, buffer->device_addr); diff --git a/driver/vidc/src/msm_vidc_memory.c b/driver/vidc/src/msm_vidc_memory.c index ec3383df9b..80a7bf7aba 100644 --- a/driver/vidc/src/msm_vidc_memory.c +++ b/driver/vidc/src/msm_vidc_memory.c @@ -28,8 +28,7 @@ struct msm_vidc_type_size_name { static const struct msm_vidc_type_size_name buftype_size_name_arr[] = { {MSM_MEM_POOL_BUFFER, sizeof(struct msm_vidc_buffer), "MSM_MEM_POOL_BUFFER" }, - {MSM_MEM_POOL_MAP, sizeof(struct msm_vidc_map), "MSM_MEM_POOL_MAP" }, - {MSM_MEM_POOL_ALLOC, sizeof(struct msm_vidc_alloc), "MSM_MEM_POOL_ALLOC" }, + {MSM_MEM_POOL_ALLOC_MAP, sizeof(struct msm_vidc_mem), "MSM_MEM_POOL_ALLOC_MAP" }, {MSM_MEM_POOL_TIMESTAMP, sizeof(struct msm_vidc_timestamp), "MSM_MEM_POOL_TIMESTAMP" }, {MSM_MEM_POOL_DMABUF, sizeof(struct msm_memory_dmabuf), "MSM_MEM_POOL_DMABUF" }, {MSM_MEM_POOL_PACKET, sizeof(struct hfi_pending_packet) + MSM_MEM_POOL_PACKET_SIZE, @@ -410,112 +409,72 @@ static struct sg_table *msm_vidc_dma_buf_map_attachment( return table; } -static int msm_vidc_memory_map(struct msm_vidc_core *core, struct msm_vidc_map *map) +static int msm_vidc_memory_alloc_map(struct msm_vidc_core *core, struct msm_vidc_mem *mem) { - int rc = 0; - struct dma_buf_attachment *attach = NULL; - struct sg_table *table = NULL; + int size = 0; struct context_bank_info *cb = NULL; - if (!core || !map) { - d_vpr_e("%s: invalid params\n", __func__); - return -EINVAL; - } - - if (map->refcount) { - map->refcount++; - goto exit; - } - - cb = msm_vidc_get_context_bank_for_region(core, map->region); - if (!cb) { - d_vpr_e("%s: Failed to get context bank device\n", - __func__); - rc = -EIO; - goto error_cb; - } - - /* Prepare a dma buf for dma on the given device */ - attach = msm_vidc_dma_buf_attach(core, map->dmabuf, cb->dev); - if (IS_ERR_OR_NULL(attach)) { - rc = PTR_ERR(attach) ? PTR_ERR(attach) : -ENOMEM; - d_vpr_e("Failed to attach dmabuf\n"); - goto error_attach; - } - - table = msm_vidc_dma_buf_map_attachment(core, attach); - if (IS_ERR_OR_NULL(table)) { - rc = PTR_ERR(table) ? PTR_ERR(table) : -ENOMEM; - d_vpr_e("Failed to map table\n"); - goto error_table; - } - - map->device_addr = sg_dma_address(table->sgl); - map->table = table; - map->attach = attach; - map->refcount++; - -exit: - d_vpr_l( - "%s: type %11s, device_addr %#llx, refcount %d, region %d\n", - __func__, buf_name(map->type), map->device_addr, map->refcount, map->region); - - return 0; - -error_table: - msm_vidc_dma_buf_detach(core, map->dmabuf, attach); -error_attach: -error_cb: - return rc; -} - -static int msm_vidc_memory_unmap(struct msm_vidc_core *core, - struct msm_vidc_map *map) -{ - int rc = 0; - - if (!core || !map) { + if (!mem) { d_vpr_e("%s: invalid params\n", __func__); return -EINVAL; } - if (map->refcount) { - map->refcount--; - } else { - d_vpr_e("unmap called while refcount is zero already\n"); + size = ALIGN(mem->size, SZ_4K); + mem->attrs = DMA_ATTR_WRITE_COMBINE; + + cb = msm_vidc_get_context_bank_for_region(core, mem->region); + if (!cb) { + d_vpr_e("%s: Failed to get context bank device\n", + __func__); + return -EIO; + } + + mem->kvaddr = dma_alloc_attrs(cb->dev, size, &mem->device_addr, GFP_KERNEL, + mem->attrs); + if (!mem->kvaddr) { + d_vpr_e("%s: dma_alloc_attrs returned NULL\n", __func__); + return -ENOMEM; + } + + d_vpr_h( + "%s: dmabuf %pK, size %d, buffer_type %s, secure %d, region %d\n", + __func__, mem->kvaddr, mem->size, buf_name(mem->type), + mem->secure, mem->region); + + return 0; +} + +static int msm_vidc_memory_unmap_free(struct msm_vidc_core *core, struct msm_vidc_mem *mem) +{ + int rc = 0; + struct context_bank_info *cb = NULL; + + if (!mem || !mem->device_addr || !mem->kvaddr) { + d_vpr_e("%s: invalid params\n", __func__); return -EINVAL; } - d_vpr_l( - "%s: type %11s, device_addr %#llx, refcount %d, region %d\n", - __func__, buf_name(map->type), map->device_addr, map->refcount, map->region); + d_vpr_h( + "%s: dmabuf %pK, size %d, kvaddr %pK, buffer_type %s, secure %d, region %d\n", + __func__, mem->device_addr, mem->size, mem->kvaddr, buf_name(mem->type), + mem->secure, mem->region); - if (map->refcount) - goto exit; + cb = msm_vidc_get_context_bank_for_region(core, mem->region); + if (!cb) { + d_vpr_e("%s: Failed to get context bank device\n", + __func__); + return -EIO; + } - msm_vidc_dma_buf_unmap_attachment(core, map->attach, map->table); - msm_vidc_dma_buf_detach(core, map->dmabuf, map->attach); + dma_free_attrs(cb->dev, mem->size, mem->kvaddr, mem->device_addr, + mem->attrs); - map->device_addr = 0x0; - map->attach = NULL; - map->table = NULL; + mem->kvaddr = NULL; + mem->device_addr = 0; -exit: return rc; } -static int msm_vidc_memory_alloc(struct msm_vidc_core *core, struct msm_vidc_alloc *mem) -{ - d_vpr_e("%s: unsupported\n", __func__); - return -EINVAL; -} - -static int msm_vidc_memory_free(struct msm_vidc_core *core, struct msm_vidc_alloc *mem) -{ - d_vpr_e("%s: unsupported\n", __func__); - return -EINVAL; -} - static u32 msm_vidc_buffer_region(struct msm_vidc_inst *inst, enum msm_vidc_buffer_type buffer_type) { @@ -530,10 +489,8 @@ static struct msm_vidc_memory_ops msm_mem_ops = { .dma_buf_detach = msm_vidc_dma_buf_detach, .dma_buf_map_attachment = msm_vidc_dma_buf_map_attachment, .dma_buf_unmap_attachment = msm_vidc_dma_buf_unmap_attachment, - .memory_map = msm_vidc_memory_map, - .memory_unmap = msm_vidc_memory_unmap, - .memory_alloc = msm_vidc_memory_alloc, - .memory_free = msm_vidc_memory_free, + .memory_alloc_map = msm_vidc_memory_alloc_map, + .memory_unmap_free = msm_vidc_memory_unmap_free, .buffer_region = msm_vidc_buffer_region, }; diff --git a/driver/vidc/src/msm_vidc_memory_ext.c b/driver/vidc/src/msm_vidc_memory_ext.c index c575514a64..50712b45ce 100644 --- a/driver/vidc/src/msm_vidc_memory_ext.c +++ b/driver/vidc/src/msm_vidc_memory_ext.c @@ -79,7 +79,7 @@ static struct dma_buf_attachment *msm_vidc_dma_buf_attach_ext(struct msm_vidc_co return attach; } -static int msm_vidc_memory_free_ext(struct msm_vidc_core *core, struct msm_vidc_alloc *mem) +static int msm_vidc_memory_free_ext(struct msm_vidc_core *core, struct msm_vidc_mem *mem) { int rc = 0; @@ -114,7 +114,7 @@ static int msm_vidc_memory_free_ext(struct msm_vidc_core *core, struct msm_vidc_ return rc; } -static int msm_vidc_memory_alloc_ext(struct msm_vidc_core *core, struct msm_vidc_alloc *mem) +static int msm_vidc_memory_alloc_ext(struct msm_vidc_core *core, struct msm_vidc_mem *mem) { int rc = 0; int size = 0; @@ -224,39 +224,39 @@ error: return rc; } -static int msm_vidc_memory_map_ext(struct msm_vidc_core *core, struct msm_vidc_map *map) +static int msm_vidc_memory_map_ext(struct msm_vidc_core *core, struct msm_vidc_mem *mem) { int rc = 0; struct dma_buf_attachment *attach = NULL; struct sg_table *table = NULL; struct context_bank_info *cb = NULL; - if (!core || !map) { + if (!core || !mem) { d_vpr_e("%s: invalid params\n", __func__); return -EINVAL; } - if (map->refcount) { - map->refcount++; + if (mem->refcount) { + mem->refcount++; goto exit; } /* reject non-secure mapping request for a secure buffer(or vice versa) */ - if (map->region == MSM_VIDC_NON_SECURE || map->region == MSM_VIDC_NON_SECURE_PIXEL) { - if (!is_non_secure_buffer(map->dmabuf)) { + if (mem->region == MSM_VIDC_NON_SECURE || mem->region == MSM_VIDC_NON_SECURE_PIXEL) { + if (!is_non_secure_buffer(mem->dmabuf)) { d_vpr_e("%s: secure buffer mapping to non-secure region %d not allowed\n", - __func__, map->region); + __func__, mem->region); return -EINVAL; } } else { - if (is_non_secure_buffer(map->dmabuf)) { + if (is_non_secure_buffer(mem->dmabuf)) { d_vpr_e("%s: non-secure buffer mapping to secure region %d not allowed\n", - __func__, map->region); + __func__, mem->region); return -EINVAL; } } - cb = msm_vidc_get_context_bank_for_region(core, map->region); + cb = msm_vidc_get_context_bank_for_region(core, mem->region); if (!cb) { d_vpr_e("%s: Failed to get context bank device\n", __func__); @@ -265,7 +265,7 @@ static int msm_vidc_memory_map_ext(struct msm_vidc_core *core, struct msm_vidc_m } /* Prepare a dma buf for dma on the given device */ - attach = msm_vidc_dma_buf_attach_ext(core, map->dmabuf, cb->dev); + attach = msm_vidc_dma_buf_attach_ext(core, mem->dmabuf, cb->dev); if (IS_ERR_OR_NULL(attach)) { rc = PTR_ERR(attach) ? PTR_ERR(attach) : -ENOMEM; d_vpr_e("Failed to attach dmabuf\n"); @@ -279,24 +279,59 @@ static int msm_vidc_memory_map_ext(struct msm_vidc_core *core, struct msm_vidc_m goto error_table; } - map->device_addr = sg_dma_address(table->sgl); - map->table = table; - map->attach = attach; - map->refcount++; + mem->device_addr = sg_dma_address(table->sgl); + mem->table = table; + mem->attach = attach; + mem->refcount++; exit: d_vpr_l("%s: type %11s, device_addr %#llx, refcount %d, region %d\n", - __func__, buf_name(map->type), map->device_addr, map->refcount, map->region); + __func__, buf_name(mem->type), mem->device_addr, mem->refcount, mem->region); return 0; error_table: - call_mem_op(core, dma_buf_detach, core, map->dmabuf, attach); + call_mem_op(core, dma_buf_detach, core, mem->dmabuf, attach); error_attach: error_cb: return rc; } +static int msm_vidc_memory_unmap_ext(struct msm_vidc_core *core, + struct msm_vidc_mem *mem) +{ + int rc = 0; + + if (!core || !mem) { + d_vpr_e("%s: invalid params\n", __func__); + return -EINVAL; + } + + if (mem->refcount) { + mem->refcount--; + } else { + d_vpr_e("unmap called while refcount is zero already\n"); + return -EINVAL; + } + + d_vpr_l( + "%s: type %11s, device_addr %#llx, refcount %d, region %d\n", + __func__, buf_name(mem->type), mem->device_addr, mem->refcount, mem->region); + + if (mem->refcount) + goto exit; + + call_mem_op(core, dma_buf_unmap_attachment, core, mem->attach, mem->table); + call_mem_op(core, dma_buf_detach, core, mem->dmabuf, mem->attach); + + mem->device_addr = 0x0; + mem->attach = NULL; + mem->table = NULL; + +exit: + return rc; +} + static u32 msm_vidc_buffer_region_ext(struct msm_vidc_inst *inst, enum msm_vidc_buffer_type buffer_type) { @@ -379,17 +414,54 @@ static u32 msm_vidc_buffer_region_ext(struct msm_vidc_inst *inst, return region; } +static int msm_vidc_memory_alloc_map_ext(struct msm_vidc_core *core, struct msm_vidc_mem *mem) +{ + int rc = 0; + + rc = msm_vidc_memory_alloc_ext(core, mem); + if (rc) { + d_vpr_e("%s: memory_alloc failed\n", __func__); + return -EINVAL; + } + + rc = msm_vidc_memory_map_ext(core, mem); + if (rc) { + d_vpr_e("%s: memory_map failed\n", __func__); + return -EINVAL; + } + + return rc; +} + +static int msm_vidc_memory_unmap_free_ext(struct msm_vidc_core *core, struct msm_vidc_mem *mem) +{ + int rc = 0; + + rc = msm_vidc_memory_unmap_ext(core, mem); + if (rc) { + d_vpr_e("%s: memory_unmap failed\n", __func__); + return -EINVAL; + } + + rc = msm_vidc_memory_free_ext(core, mem); + if (rc) { + d_vpr_e("%s: memory_free failed\n", __func__); + return -EINVAL; + } + + return rc; +} + struct msm_vidc_memory_ops *get_mem_ops_ext(void) { struct msm_vidc_memory_ops *mem_ops = get_mem_ops(); static struct msm_vidc_memory_ops mem_ops_ext; memcpy(&mem_ops_ext, mem_ops, sizeof(struct msm_vidc_memory_ops)); - mem_ops_ext.dma_buf_attach = msm_vidc_dma_buf_attach_ext; - mem_ops_ext.memory_free = msm_vidc_memory_free_ext; - mem_ops_ext.memory_alloc = msm_vidc_memory_alloc_ext; - mem_ops_ext.memory_map = msm_vidc_memory_map_ext; - mem_ops_ext.buffer_region = msm_vidc_buffer_region_ext; + mem_ops_ext.dma_buf_attach = msm_vidc_dma_buf_attach_ext; + mem_ops_ext.memory_alloc_map = msm_vidc_memory_alloc_map_ext; + mem_ops_ext.memory_unmap_free = msm_vidc_memory_unmap_free_ext; + mem_ops_ext.buffer_region = msm_vidc_buffer_region_ext; return &mem_ops_ext; } diff --git a/driver/vidc/src/venus_hfi_queue.c b/driver/vidc/src/venus_hfi_queue.c index 6fe2aaf82f..f4e2a07a71 100644 --- a/driver/vidc/src/venus_hfi_queue.c +++ b/driver/vidc/src/venus_hfi_queue.c @@ -424,10 +424,8 @@ void venus_hfi_queue_deinit(struct msm_vidc_core *core) return; } - call_mem_op(core, memory_unmap, core, &core->iface_q_table.map); - call_mem_op(core, memory_free, core, &core->iface_q_table.alloc); - call_mem_op(core, memory_unmap, core, &core->sfr.map); - call_mem_op(core, memory_free, core, &core->sfr.alloc); + call_mem_op(core, memory_unmap_free, core, &core->iface_q_table.mem); + call_mem_op(core, memory_unmap_free, core, &core->sfr.mem); for (i = 0; i < VIDC_IFACEQ_NUMQ; i++) { core->iface_queues[i].q_hdr = NULL; @@ -487,8 +485,7 @@ int venus_hfi_queue_init(struct msm_vidc_core *core) struct hfi_queue_table_header *q_tbl_hdr; struct hfi_queue_header *q_hdr; struct msm_vidc_iface_q_info *iface_q; - struct msm_vidc_alloc alloc; - struct msm_vidc_map map; + struct msm_vidc_mem mem; int offset = 0; u32 i; @@ -500,39 +497,28 @@ int venus_hfi_queue_init(struct msm_vidc_core *core) return 0; } - memset(&alloc, 0, sizeof(alloc)); - alloc.type = MSM_VIDC_BUF_QUEUE; - alloc.region = MSM_VIDC_NON_SECURE; - alloc.size = TOTAL_QSIZE; - alloc.secure = false; - alloc.map_kernel = true; - rc = call_mem_op(core, memory_alloc, core, &alloc); + memset(&mem, 0, sizeof(mem)); + mem.type = MSM_VIDC_BUF_QUEUE; + mem.region = MSM_VIDC_NON_SECURE; + mem.size = TOTAL_QSIZE; + mem.secure = false; + mem.map_kernel = true; + rc = call_mem_op(core, memory_alloc_map, core, &mem); if (rc) { - d_vpr_e("%s: alloc failed\n", __func__); + d_vpr_e("%s: alloc and map failed\n", __func__); goto fail_alloc_queue; } - core->iface_q_table.align_virtual_addr = alloc.kvaddr; - core->iface_q_table.alloc = alloc; - - memset(&map, 0, sizeof(map)); - map.type = alloc.type; - map.region = alloc.region; - map.dmabuf = alloc.dmabuf; - rc = call_mem_op(core, memory_map, core, &map); - if (rc) { - d_vpr_e("%s: alloc failed\n", __func__); - goto fail_alloc_queue; - } - core->iface_q_table.align_device_addr = map.device_addr; - core->iface_q_table.map = map; + core->iface_q_table.align_virtual_addr = mem.kvaddr; + core->iface_q_table.align_device_addr = mem.device_addr; + core->iface_q_table.mem = mem; core->iface_q_table.mem_size = VIDC_IFACEQ_TABLE_SIZE; offset += core->iface_q_table.mem_size; for (i = 0; i < VIDC_IFACEQ_NUMQ; i++) { iface_q = &core->iface_queues[i]; - iface_q->q_array.align_device_addr = map.device_addr + offset; - iface_q->q_array.align_virtual_addr = (void*)((char*)alloc.kvaddr + offset); + iface_q->q_array.align_device_addr = mem.device_addr + offset; + iface_q->q_array.align_virtual_addr = (void *)((char *)mem.kvaddr + offset); iface_q->q_array.mem_size = VIDC_IFACEQ_QUEUE_SIZE; offset += iface_q->q_array.mem_size; iface_q->q_hdr = VIDC_IFACEQ_GET_QHDR_START_ADDR( @@ -572,31 +558,20 @@ int venus_hfi_queue_init(struct msm_vidc_core *core) q_hdr->qhdr_rx_req = 0; /* sfr buffer */ - memset(&alloc, 0, sizeof(alloc)); - alloc.type = MSM_VIDC_BUF_QUEUE; - alloc.region = MSM_VIDC_NON_SECURE; - alloc.size = ALIGNED_SFR_SIZE; - alloc.secure = false; - alloc.map_kernel = true; - rc = call_mem_op(core, memory_alloc, core, &alloc); + memset(&mem, 0, sizeof(mem)); + mem.type = MSM_VIDC_BUF_QUEUE; + mem.region = MSM_VIDC_NON_SECURE; + mem.size = ALIGNED_SFR_SIZE; + mem.secure = false; + mem.map_kernel = true; + rc = call_mem_op(core, memory_alloc_map, core, &mem); if (rc) { - d_vpr_e("%s: sfr alloc failed\n", __func__); + d_vpr_e("%s: sfr alloc and map failed\n", __func__); goto fail_alloc_queue; } - core->sfr.align_virtual_addr = alloc.kvaddr; - core->sfr.alloc = alloc; - - memset(&map, 0, sizeof(map)); - map.type = alloc.type; - map.region = alloc.region; - map.dmabuf = alloc.dmabuf; - rc = call_mem_op(core, memory_map, core, &map); - if (rc) { - d_vpr_e("%s: sfr map failed\n", __func__); - goto fail_alloc_queue; - } - core->sfr.align_device_addr = map.device_addr; - core->sfr.map = map; + core->sfr.align_virtual_addr = mem.kvaddr; + core->sfr.align_device_addr = mem.device_addr; + core->sfr.mem = mem; core->sfr.mem_size = ALIGNED_SFR_SIZE; /* write sfr buffer size in first word */