mirror of
https://github.com/hardkernel/linux.git
synced 2026-06-09 04:10:18 +09:00
vidro/rockchip: Fix rga2 driver
1.If rga get the mmu error, we must unlock the lock or it will lead the next frame timeout. 2.calculate the rga mmu buf back length size in the rga time out handler or it will lead the next frame get mmu lentch wrong. Change-Id: If85751bd292774a1d0ef9693b7f8ad92a4727c07 Signed-off-by: Zikim,Wei <wzq@rock-chips.com>
This commit is contained in:
@@ -538,21 +538,19 @@ static void rga2_try_set_reg(void)
|
||||
}
|
||||
}
|
||||
|
||||
/* Caller must hold rga_service.lock */
|
||||
static void rga2_del_running_list(void)
|
||||
{
|
||||
struct rga2_mmu_buf_t *tbuf = &rga2_mmu_buf;
|
||||
struct rga2_reg *reg;
|
||||
|
||||
while(!list_empty(&rga2_service.running))
|
||||
{
|
||||
reg = list_entry(rga2_service.running.next, struct rga2_reg, status_link);
|
||||
|
||||
if(reg->MMU_len != 0)
|
||||
{
|
||||
if (rga2_mmu_buf.back + reg->MMU_len > 2*rga2_mmu_buf.size)
|
||||
rga2_mmu_buf.back = reg->MMU_len + rga2_mmu_buf.size;
|
||||
while (!list_empty(&rga2_service.running)) {
|
||||
reg = list_entry(rga2_service.running.next, struct rga2_reg,
|
||||
status_link);
|
||||
if (reg->MMU_len && tbuf) {
|
||||
if (tbuf->back + reg->MMU_len > 2 * tbuf->size)
|
||||
tbuf->back = reg->MMU_len + tbuf->size;
|
||||
else
|
||||
rga2_mmu_buf.back += reg->MMU_len;
|
||||
tbuf->back += reg->MMU_len;
|
||||
}
|
||||
atomic_sub(1, ®->session->task_running);
|
||||
atomic_sub(1, &rga2_service.total_running);
|
||||
@@ -567,33 +565,31 @@ static void rga2_del_running_list(void)
|
||||
}
|
||||
}
|
||||
|
||||
/* Caller must hold rga_service.lock */
|
||||
static void rga2_del_running_list_timeout(void)
|
||||
{
|
||||
struct rga2_reg *reg;
|
||||
struct rga2_mmu_buf_t *tbuf = &rga2_mmu_buf;
|
||||
struct rga2_reg *reg;
|
||||
|
||||
while(!list_empty(&rga2_service.running))
|
||||
{
|
||||
reg = list_entry(rga2_service.running.next, struct rga2_reg, status_link);
|
||||
|
||||
if(reg->MMU_base != NULL)
|
||||
{
|
||||
kfree(reg->MMU_base);
|
||||
}
|
||||
|
||||
atomic_sub(1, ®->session->task_running);
|
||||
atomic_sub(1, &rga2_service.total_running);
|
||||
|
||||
rga2_soft_reset();
|
||||
|
||||
if(list_empty(®->session->waiting))
|
||||
{
|
||||
atomic_set(®->session->done, 1);
|
||||
wake_up(®->session->wait);
|
||||
}
|
||||
|
||||
rga2_reg_deinit(reg);
|
||||
}
|
||||
while (!list_empty(&rga2_service.running)) {
|
||||
reg = list_entry(rga2_service.running.next, struct rga2_reg,
|
||||
status_link);
|
||||
kfree(reg->MMU_base);
|
||||
if (reg->MMU_len && tbuf) {
|
||||
if (tbuf->back + reg->MMU_len > 2 * tbuf->size)
|
||||
tbuf->back = reg->MMU_len + tbuf->size;
|
||||
else
|
||||
tbuf->back += reg->MMU_len;
|
||||
}
|
||||
atomic_sub(1, ®->session->task_running);
|
||||
atomic_sub(1, &rga2_service.total_running);
|
||||
rga2_soft_reset();
|
||||
if (list_empty(®->session->waiting)) {
|
||||
atomic_set(®->session->done, 1);
|
||||
wake_up(®->session->wait);
|
||||
}
|
||||
rga2_reg_deinit(reg);
|
||||
}
|
||||
return;
|
||||
}
|
||||
|
||||
static int rga2_convert_dma_buf(struct rga2_req *req)
|
||||
|
||||
@@ -73,34 +73,41 @@ static int rga2_mmu_buf_get(struct rga2_mmu_buf_t *t, uint32_t size)
|
||||
return 0;
|
||||
}
|
||||
|
||||
static int rga2_mmu_buf_get_try(struct rga2_mmu_buf_t *t, uint32_t size)
|
||||
{
|
||||
mutex_lock(&rga2_service.lock);
|
||||
if((t->back - t->front) > t->size) {
|
||||
if(t->front + size > t->back - t->size) {
|
||||
pr_info("front %d, back %d dsize %d size %d", t->front, t->back, t->size, size);
|
||||
return -1;
|
||||
}
|
||||
}
|
||||
else {
|
||||
if((t->front + size) > t->back) {
|
||||
pr_info("front %d, back %d dsize %d size %d", t->front, t->back, t->size, size);
|
||||
return -1;
|
||||
}
|
||||
|
||||
if(t->front + size > t->size) {
|
||||
if (size > (t->back - t->size)) {
|
||||
pr_info("front %d, back %d dsize %d size %d", t->front, t->back, t->size, size);
|
||||
return -1;
|
||||
}
|
||||
t->front = 0;
|
||||
}
|
||||
}
|
||||
mutex_unlock(&rga2_service.lock);
|
||||
|
||||
return 0;
|
||||
}
|
||||
|
||||
static int rga2_mmu_buf_get_try(struct rga2_mmu_buf_t *t, uint32_t size)
|
||||
{
|
||||
int ret = 0;
|
||||
|
||||
mutex_lock(&rga2_service.lock);
|
||||
if ((t->back - t->front) > t->size) {
|
||||
if (t->front + size > t->back - t->size) {
|
||||
pr_info("front %d, back %d dsize %d size %d",
|
||||
t->front, t->back, t->size, size);
|
||||
ret = -ENOMEM;
|
||||
goto out;
|
||||
}
|
||||
} else {
|
||||
if ((t->front + size) > t->back) {
|
||||
pr_info("front %d, back %d dsize %d size %d",
|
||||
t->front, t->back, t->size, size);
|
||||
ret = -ENOMEM;
|
||||
goto out;
|
||||
}
|
||||
|
||||
if (t->front + size > t->size) {
|
||||
if (size > (t->back - t->size)) {
|
||||
pr_info("front %d, back %d dsize %d size %d",
|
||||
t->front, t->back, t->size, size);
|
||||
ret = -ENOMEM;
|
||||
goto out;
|
||||
}
|
||||
t->front = 0;
|
||||
}
|
||||
}
|
||||
out:
|
||||
mutex_unlock(&rga2_service.lock);
|
||||
return ret;
|
||||
}
|
||||
|
||||
static int rga2_mem_size_cal(unsigned long Mem, uint32_t MemSize, unsigned long *StartAddr)
|
||||
{
|
||||
unsigned long start, end;
|
||||
|
||||
Reference in New Issue
Block a user