mirror of
https://github.com/hardkernel/linux.git
synced 2026-06-07 11:26:02 +09:00
video: rockchip: rga3: fixup current->mm is null in multithreading
save current->mm on rga_job Signed-off-by: Li Huang <putin.li@rock-chips.com> Change-Id: I04ea720fb20a4e88eecb07c776c1c9c7c90f6ff6
This commit is contained in:
@@ -43,6 +43,7 @@
|
||||
#include <linux/wait.h>
|
||||
#include <linux/wakelock.h>
|
||||
#include <linux/pm_runtime.h>
|
||||
#include <linux/sched/mm.h>
|
||||
|
||||
#include <asm/cacheflush.h>
|
||||
|
||||
@@ -185,6 +186,8 @@ struct rga_job {
|
||||
struct dma_buf *dma_buf_dst;
|
||||
struct dma_buf *dma_buf_els;
|
||||
|
||||
/* for rga2 virtual_address */
|
||||
struct mm_struct *mm;
|
||||
struct rga2_mmu_other_t vir_page_table;
|
||||
|
||||
struct dma_fence *out_fence;
|
||||
|
||||
@@ -402,7 +402,8 @@ static int rga2_user_memory_check(struct page **pages, u32 w, u32 h, u32 format,
|
||||
|
||||
static int rga2_MapUserMemory(struct page **pages, uint32_t *pageTable,
|
||||
unsigned long Memory, uint32_t pageCount,
|
||||
int writeFlag, int map, struct rga_scheduler_t *scheduler)
|
||||
int writeFlag, int map, struct rga_scheduler_t *scheduler,
|
||||
struct mm_struct *mm)
|
||||
{
|
||||
struct vm_area_struct *vma;
|
||||
int32_t result;
|
||||
@@ -423,25 +424,25 @@ static int rga2_MapUserMemory(struct page **pages, uint32_t *pageTable,
|
||||
status = 0;
|
||||
|
||||
#if LINUX_VERSION_CODE >= KERNEL_VERSION(5, 10, 0)
|
||||
mmap_read_lock(current->mm);
|
||||
mmap_read_lock(mm);
|
||||
#else
|
||||
down_read(¤t->mm->mmap_sem);
|
||||
down_read(&mm->mmap_sem);
|
||||
#endif
|
||||
|
||||
#if LINUX_VERSION_CODE >= KERNEL_VERSION(4, 4, 168) && \
|
||||
LINUX_VERSION_CODE < KERNEL_VERSION(4, 5, 0)
|
||||
result = get_user_pages(current, current->mm, Memory << PAGE_SHIFT,
|
||||
result = get_user_pages(current, mm, Memory << PAGE_SHIFT,
|
||||
pageCount, writeFlag ? FOLL_WRITE : 0,
|
||||
pages, NULL);
|
||||
#elif LINUX_VERSION_CODE < KERNEL_VERSION(4, 6, 0)
|
||||
result = get_user_pages(current, current->mm, Memory << PAGE_SHIFT,
|
||||
result = get_user_pages(current, mm, Memory << PAGE_SHIFT,
|
||||
pageCount, writeFlag, 0, pages, NULL);
|
||||
#elif LINUX_VERSION_CODE < KERNEL_VERSION(5, 10, 0)
|
||||
result = get_user_pages_remote(current, current->mm,
|
||||
result = get_user_pages_remote(current, mm,
|
||||
Memory << PAGE_SHIFT,
|
||||
pageCount, writeFlag, pages, NULL, NULL);
|
||||
#else
|
||||
result = get_user_pages_remote(current->mm, Memory << PAGE_SHIFT,
|
||||
result = get_user_pages_remote(mm, Memory << PAGE_SHIFT,
|
||||
pageCount, writeFlag, pages, NULL, NULL);
|
||||
#endif
|
||||
|
||||
@@ -456,9 +457,9 @@ static int rga2_MapUserMemory(struct page **pages, uint32_t *pageTable,
|
||||
put_page(pages[i]);
|
||||
|
||||
#if LINUX_VERSION_CODE >= KERNEL_VERSION(5, 10, 0)
|
||||
mmap_read_unlock(current->mm);
|
||||
mmap_read_unlock(mm);
|
||||
#else
|
||||
up_read(¤t->mm->mmap_sem);
|
||||
up_read(&mm->mmap_sem);
|
||||
#endif
|
||||
return 0;
|
||||
}
|
||||
@@ -469,7 +470,7 @@ static int rga2_MapUserMemory(struct page **pages, uint32_t *pageTable,
|
||||
}
|
||||
|
||||
for (i = 0; i < pageCount; i++) {
|
||||
vma = find_vma(current->mm, (Memory + i) << PAGE_SHIFT);
|
||||
vma = find_vma(mm, (Memory + i) << PAGE_SHIFT);
|
||||
if (!vma) {
|
||||
pr_err("failed to get vma, result = %d, pageCount = %d\n",
|
||||
result, pageCount);
|
||||
@@ -477,7 +478,7 @@ static int rga2_MapUserMemory(struct page **pages, uint32_t *pageTable,
|
||||
break;
|
||||
}
|
||||
|
||||
pgd = pgd_offset(current->mm, (Memory + i) << PAGE_SHIFT);
|
||||
pgd = pgd_offset(mm, (Memory + i) << PAGE_SHIFT);
|
||||
if (pgd_none(*pgd) || unlikely(pgd_bad(*pgd))) {
|
||||
pr_err("failed to get pgd, result = %d, pageCount = %d\n",
|
||||
result, pageCount);
|
||||
@@ -514,7 +515,7 @@ static int rga2_MapUserMemory(struct page **pages, uint32_t *pageTable,
|
||||
status = RGA_OUT_OF_RESOURCES;
|
||||
break;
|
||||
}
|
||||
pte = pte_offset_map_lock(current->mm, pmd,
|
||||
pte = pte_offset_map_lock(mm, pmd,
|
||||
(Memory + i) << PAGE_SHIFT, &ptl);
|
||||
if (pte_none(*pte)) {
|
||||
pr_err("failed to get pte, result = %d, pageCount = %d\n",
|
||||
@@ -535,9 +536,9 @@ static int rga2_MapUserMemory(struct page **pages, uint32_t *pageTable,
|
||||
}
|
||||
|
||||
#if LINUX_VERSION_CODE >= KERNEL_VERSION(5, 10, 0)
|
||||
mmap_read_unlock(current->mm);
|
||||
mmap_read_unlock(mm);
|
||||
#else
|
||||
up_read(¤t->mm->mmap_sem);
|
||||
up_read(&mm->mmap_sem);
|
||||
#endif
|
||||
|
||||
return status;
|
||||
@@ -644,7 +645,7 @@ static int rga2_mmu_flush_cache(struct rga2_mmu_other_t *reg,
|
||||
MMU_Base,
|
||||
DstStart, DstPageCount, 1,
|
||||
MMU_MAP_CLEAN |
|
||||
MMU_MAP_INVALID, scheduler);
|
||||
MMU_MAP_INVALID, scheduler, job->mm);
|
||||
#if CONFIG_ROCKCHIP_RGA_DEBUGGER
|
||||
if (RGA_DEBUG_CHECK_MODE)
|
||||
rga2_user_memory_check(&pages[0],
|
||||
@@ -763,7 +764,7 @@ static int rga2_mmu_info_BitBlt_mode(struct rga2_mmu_other_t *reg,
|
||||
} else {
|
||||
ret = rga2_MapUserMemory(&pages[0], &MMU_Base[0],
|
||||
Src0Start, Src0PageCount,
|
||||
0, MMU_MAP_CLEAN, scheduler);
|
||||
0, MMU_MAP_CLEAN, scheduler, job->mm);
|
||||
#if CONFIG_ROCKCHIP_RGA_DEBUGGER
|
||||
if (RGA_DEBUG_CHECK_MODE)
|
||||
/* TODO: */
|
||||
@@ -804,7 +805,7 @@ static int rga2_mmu_info_BitBlt_mode(struct rga2_mmu_other_t *reg,
|
||||
ret = rga2_MapUserMemory(&pages[0],
|
||||
MMU_Base + Src0MemSize,
|
||||
Src1Start, Src1PageCount,
|
||||
0, MMU_MAP_CLEAN, scheduler);
|
||||
0, MMU_MAP_CLEAN, scheduler, job->mm);
|
||||
|
||||
/* Save pagetable to unmap. */
|
||||
reg->MMU_src1_base = MMU_Base + Src0MemSize;
|
||||
@@ -837,7 +838,7 @@ static int rga2_mmu_info_BitBlt_mode(struct rga2_mmu_other_t *reg,
|
||||
+ Src0MemSize + Src1MemSize,
|
||||
DstStart, DstPageCount, 1,
|
||||
MMU_MAP_CLEAN |
|
||||
MMU_MAP_INVALID, scheduler);
|
||||
MMU_MAP_INVALID, scheduler, job->mm);
|
||||
#if CONFIG_ROCKCHIP_RGA_DEBUGGER
|
||||
if (RGA_DEBUG_CHECK_MODE)
|
||||
rga2_user_memory_check(&pages[0],
|
||||
@@ -853,7 +854,7 @@ static int rga2_mmu_info_BitBlt_mode(struct rga2_mmu_other_t *reg,
|
||||
ret = rga2_MapUserMemory(&pages[0], MMU_Base
|
||||
+ Src0MemSize + Src1MemSize,
|
||||
DstStart, DstPageCount,
|
||||
1, MMU_MAP_INVALID, scheduler);
|
||||
1, MMU_MAP_INVALID, scheduler, job->mm);
|
||||
#if CONFIG_ROCKCHIP_RGA_DEBUGGER
|
||||
if (RGA_DEBUG_CHECK_MODE)
|
||||
rga2_user_memory_check(&pages[0],
|
||||
@@ -997,7 +998,7 @@ static int rga2_mmu_info_color_palette_mode(struct rga2_mmu_other_t *reg,
|
||||
} else {
|
||||
ret = rga2_MapUserMemory(&pages[0],
|
||||
&MMU_Base[0], SrcStart, SrcPageCount,
|
||||
0, MMU_MAP_CLEAN, scheduler);
|
||||
0, MMU_MAP_CLEAN, scheduler, job->mm);
|
||||
#if CONFIG_ROCKCHIP_RGA_DEBUGGER
|
||||
if (RGA_DEBUG_CHECK_MODE)
|
||||
rga2_user_memory_check(&pages[0],
|
||||
@@ -1033,7 +1034,7 @@ static int rga2_mmu_info_color_palette_mode(struct rga2_mmu_other_t *reg,
|
||||
rga2_MapUserMemory(&pages[0],
|
||||
MMU_Base + SrcMemSize,
|
||||
DstStart, DstPageCount,
|
||||
1, MMU_MAP_INVALID, scheduler);
|
||||
1, MMU_MAP_INVALID, scheduler, job->mm);
|
||||
#if CONFIG_ROCKCHIP_RGA_DEBUGGER
|
||||
if (RGA_DEBUG_CHECK_MODE)
|
||||
rga2_user_memory_check(&pages[0],
|
||||
@@ -1137,7 +1138,7 @@ static int rga2_mmu_info_color_fill_mode(struct rga2_mmu_other_t *reg,
|
||||
} else {
|
||||
ret = rga2_MapUserMemory(&pages[0],
|
||||
&MMU_Base[0], DstStart, DstPageCount,
|
||||
1, MMU_MAP_INVALID, scheduler);
|
||||
1, MMU_MAP_INVALID, scheduler, job->mm);
|
||||
}
|
||||
if (ret < 0) {
|
||||
pr_err("map dst memory failed\n");
|
||||
@@ -1246,7 +1247,7 @@ static int rga2_mmu_info_update_palette_table_mode(struct rga2_mmu_other_t *reg,
|
||||
} else {
|
||||
ret = rga2_MapUserMemory(&pages[0],
|
||||
&MMU_Base[0], LutStart,
|
||||
LutPageCount, 0, MMU_MAP_CLEAN, scheduler);
|
||||
LutPageCount, 0, MMU_MAP_CLEAN, scheduler, job->mm);
|
||||
}
|
||||
if (ret < 0) {
|
||||
pr_err("rga2 map palette memory failed\n");
|
||||
|
||||
@@ -218,6 +218,8 @@ void rga_job_done(struct rga_scheduler_t *rga_scheduler, int ret)
|
||||
|
||||
kref_put(&rga_scheduler->pd_refcount, rga_kref_disable_power);
|
||||
|
||||
mmdrop(job->mm);
|
||||
|
||||
if (job->out_fence)
|
||||
dma_fence_signal(job->out_fence);
|
||||
|
||||
@@ -707,6 +709,9 @@ int rga_commit(struct rga_req *rga_command_base, int flags)
|
||||
return ret;
|
||||
}
|
||||
|
||||
mmgrab(current->mm);
|
||||
job->mm = current->mm;
|
||||
|
||||
if (flags == RGA_BLIT_ASYNC) {
|
||||
ret = rga_out_fence_alloc(job);
|
||||
if (ret) {
|
||||
|
||||
Reference in New Issue
Block a user