gpu: add lock before use other process's task
author杜坤明 <dkm@rockchip.com>
Mon, 28 Mar 2011 04:01:00 +0000 (12:01 +0800)
committer杜坤明 <dkm@rockchip.com>
Mon, 28 Mar 2011 04:01:00 +0000 (12:01 +0800)
drivers/staging/rk29/vivante/hal/os/linux/kernel/gc_hal_kernel_driver.c
drivers/staging/rk29/vivante/hal/os/linux/kernel/gc_hal_kernel_linux.h [changed mode: 0644->0755]
drivers/staging/rk29/vivante/hal/os/linux/kernel/gc_hal_kernel_os.c

index 8846dba3cfd670ddee3dcbe58b64317fc1ef4763..5a9dea126e23b7b215a92a678495fdf59887d86c 100755 (executable)
@@ -755,7 +755,7 @@ static void gpu_early_suspend(struct early_suspend *h)
 {
        gceSTATUS status;
     
-    printk("Enter %s \n", __func__);
+    //printk("Enter %s \n", __func__);
 
     msleep(50); //Wait for gpu finish
 
@@ -767,14 +767,14 @@ static void gpu_early_suspend(struct early_suspend *h)
                return;
        }
 
-       printk("Exit %s \n", __func__);
+       //printk("Exit %s \n", __func__);
 }
 
 static void gpu_early_resume(struct early_suspend *h)
 {
        gceSTATUS status;
     
-    printk("Enter %s \n", __func__);
+    //printk("Enter %s \n", __func__);
 
        status = gckHARDWARE_SetPowerManagementState(galDevice->kernel->hardware, gcvPOWER_IDLE);
 
@@ -786,7 +786,7 @@ static void gpu_early_resume(struct early_suspend *h)
                return;
        }
 
-       printk("Exit %s \n", __func__);
+       //printk("Exit %s \n", __func__);
 }
 
 struct early_suspend gpu_early_suspend_info = {
@@ -857,7 +857,7 @@ static int __devinit gpu_suspend(struct platform_device *dev, pm_message_t state
        gceSTATUS status;
        gckGALDEVICE device;
     
-    printk("Enter %s \n", __func__);
+    //printk("Enter %s \n", __func__);
 
        device = platform_get_drvdata(dev);
 
@@ -871,7 +871,7 @@ static int __devinit gpu_suspend(struct platform_device *dev, pm_message_t state
                return -1;
        }
 
-       printk("Exit %s \n", __func__);
+       //printk("Exit %s \n", __func__);
 
        return 0;
 }
@@ -881,7 +881,7 @@ static int __devinit gpu_resume(struct platform_device *dev)
        gceSTATUS status;
        gckGALDEVICE device;
     
-    printk("Enter %s \n", __func__);
+    //printk("Enter %s \n", __func__);
 
        device = platform_get_drvdata(dev);
 
@@ -895,7 +895,7 @@ static int __devinit gpu_resume(struct platform_device *dev)
                return -1;
        }
 
-       printk("Exit %s \n", __func__);
+       //printk("Exit %s \n", __func__);
     
        return 0;
 }
old mode 100644 (file)
new mode 100755 (executable)
index de767ea..3cc30d7
@@ -57,7 +57,7 @@
 #include "gc_hal_kernel_os.h"
 
 #if LINUX_VERSION_CODE >= KERNEL_VERSION(2,6,31)
-#define FIND_TASK_BY_PID(x) pid_task(find_vpid(x), PIDTYPE_PID)
+#define FIND_TASK_BY_PID(x) get_pid_task(find_vpid(x), PIDTYPE_PID)
 #elif LINUX_VERSION_CODE >= KERNEL_VERSION(2,6,27)
 #define FIND_TASK_BY_PID(x) find_task_by_vpid(x)
 #else
index 10faa6fa3a0c8fe0a8d209d0cbc9fc170021075c..7d5f731e0f3369259a78cd006138ffaab786a45d 100755 (executable)
@@ -1105,6 +1105,7 @@ gckOS_UnmapMemory(
     PLINUX_MDL_MAP          mdlMap;
     PLINUX_MDL              mdl = (PLINUX_MDL)Physical;
     struct task_struct *    task;
+    struct mm_struct *      mm;
 
     /* Verify the arguments. */
     gcmkVERIFY_OBJECT(Os, gcvOBJ_OS);
@@ -1143,12 +1144,19 @@ gckOS_UnmapMemory(
 
         /* Get the current pointer for the task with stored pid. */
         task = FIND_TASK_BY_PID(mdlMap->pid);
+        if(task) {
+            mm = get_task_mm(task);
+            put_task_struct(task);
+        } else {
+            mm = gcvNULL;
+        }
 
-        if (task != gcvNULL && task->mm != gcvNULL)
+        if (mm)
         {
-            down_write(&task->mm->mmap_sem);
-            do_munmap(task->mm, (unsigned long)Logical, mdl->numPages*PAGE_SIZE);
-            up_write(&task->mm->mmap_sem);
+            down_write(&mm->mmap_sem);
+            do_munmap(mm, (unsigned long)Logical, mdl->numPages*PAGE_SIZE);
+            up_write(&mm->mmap_sem);
+            mmput(mm);
         }
         else
         {
@@ -1516,6 +1524,7 @@ gceSTATUS gckOS_FreeNonPagedMemory(
     PLINUX_MDL              mdl;
     PLINUX_MDL_MAP          mdlMap;
     struct task_struct *    task;
+    struct mm_struct *      mm;
 
 #ifdef NO_DMA_COHERENT
     unsigned                size;
@@ -1567,12 +1576,18 @@ gceSTATUS gckOS_FreeNonPagedMemory(
         {
             /* Get the current pointer for the task with stored pid. */
             task = FIND_TASK_BY_PID(mdlMap->pid);
+            if(task) {
+                mm = get_task_mm(task);
+                put_task_struct(task);
+            } else {
+                mm = gcvNULL;
+            }
 
-            if (task != gcvNULL && task->mm != gcvNULL)
+            if (mm)
             {
-                down_write(&task->mm->mmap_sem);
+                down_write(&mm->mmap_sem);
 
-                if (do_munmap(task->mm,
+                if (do_munmap(mm,
                             (unsigned long)mdlMap->vmaAddr,
                             mdl->numPages * PAGE_SIZE) < 0)
                 {
@@ -1585,7 +1600,8 @@ gceSTATUS gckOS_FreeNonPagedMemory(
                                 (gctUINT32)mdlMap->vmaAddr);
                 }
 
-                up_write(&task->mm->mmap_sem);
+                up_write(&mm->mmap_sem);
+                mmput(mm);
             }
 
             mdlMap->vmaAddr = gcvNULL;
@@ -3260,6 +3276,7 @@ gceSTATUS gckOS_UnlockPages(
     PLINUX_MDL_MAP          mdlMap;
     PLINUX_MDL              mdl = (PLINUX_MDL)Physical;
     struct task_struct *    task;
+    struct mm_struct *      mm;
 
     /* Verify the arguments. */
     gcmkVERIFY_OBJECT(Os, gcvOBJ_OS);
@@ -3283,12 +3300,19 @@ gceSTATUS gckOS_UnlockPages(
         {
             /* Get the current pointer for the task with stored pid. */
             task = FIND_TASK_BY_PID(mdlMap->pid);
+            if(task) {
+                mm = get_task_mm(task);
+                put_task_struct(task);
+            } else {
+                mm = gcvNULL;
+            }
 
-            if (task != gcvNULL && task->mm != gcvNULL)
+            if (mm)
             {
-                down_write(&task->mm->mmap_sem);
-                do_munmap(task->mm, (unsigned long)Logical, mdl->numPages * PAGE_SIZE);
-                up_write(&task->mm->mmap_sem);
+                down_write(&mm->mmap_sem);
+                do_munmap(mm, (unsigned long)Logical, mdl->numPages * PAGE_SIZE);
+                up_write(&mm->mmap_sem);
+                mmput(mm);
             }
 
             mdlMap->vmaAddr = gcvNULL;
@@ -3878,6 +3902,7 @@ gckOS_UserSignal(
             /* Success. */
             status = gcvSTATUS_OK;
         }
+        put_task_struct(task);
     }
     else
     {