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:
Zikim,Wei
2016-10-19 16:32:50 +08:00
committed by Huang, Tao
parent 0b5f9b86cc
commit f5b4aa6206
2 changed files with 65 additions and 62 deletions

View File

@@ -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, &reg->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, &reg->session->task_running);
atomic_sub(1, &rga2_service.total_running);
rga2_soft_reset();
if(list_empty(&reg->session->waiting))
{
atomic_set(&reg->session->done, 1);
wake_up(&reg->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, &reg->session->task_running);
atomic_sub(1, &rga2_service.total_running);
rga2_soft_reset();
if (list_empty(&reg->session->waiting)) {
atomic_set(&reg->session->done, 1);
wake_up(&reg->session->wait);
}
rga2_reg_deinit(reg);
}
return;
}
static int rga2_convert_dma_buf(struct rga2_req *req)

View File

@@ -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;