]> bbs.cooldavid.org Git - net-next-2.6.git/blobdiff - drivers/gpu/drm/i915/i915_gem.c
drivers/gpu/drm: Update WARN uses
[net-next-2.6.git] / drivers / gpu / drm / i915 / i915_gem.c
index 984eb6e9db033c71c49c1589a5f58f55ad3e9fd2..ef188e391406a1b3a2763e92d578c8f9e03b28b3 100644 (file)
@@ -4065,8 +4065,7 @@ i915_gem_object_pin(struct drm_gem_object *obj, uint32_t alignment)
                        alignment = i915_gem_get_gtt_alignment(obj);
                if (obj_priv->gtt_offset & (alignment - 1)) {
                        WARN(obj_priv->pin_count,
-                            "bo is already pinned with incorrect alignment:"
-                            " offset=%x, req.alignment=%x\n",
+                            "bo is already pinned with incorrect alignment: offset=%x, req.alignment=%x\n",
                             obj_priv->gtt_offset, alignment);
                        ret = i915_gem_object_unbind(obj);
                        if (ret)
@@ -4878,17 +4877,24 @@ i915_gem_phys_pwrite(struct drm_device *dev, struct drm_gem_object *obj,
                     struct drm_file *file_priv)
 {
        struct drm_i915_gem_object *obj_priv = to_intel_bo(obj);
-       void *obj_addr;
-       int ret;
-       char __user *user_data;
+       void *vaddr = obj_priv->phys_obj->handle->vaddr + args->offset;
+       char __user *user_data = (char __user *) (uintptr_t) args->data_ptr;
 
-       user_data = (char __user *) (uintptr_t) args->data_ptr;
-       obj_addr = obj_priv->phys_obj->handle->vaddr + args->offset;
+       DRM_DEBUG_DRIVER("vaddr %p, %lld\n", vaddr, args->size);
 
-       DRM_DEBUG_DRIVER("obj_addr %p, %lld\n", obj_addr, args->size);
-       ret = copy_from_user(obj_addr, user_data, args->size);
-       if (ret)
-               return -EFAULT;
+       if (__copy_from_user_inatomic_nocache(vaddr, user_data, args->size)) {
+               unsigned long unwritten;
+
+               /* The physical object once assigned is fixed for the lifetime
+                * of the obj, so we can safely drop the lock and continue
+                * to access vaddr.
+                */
+               mutex_unlock(&dev->struct_mutex);
+               unwritten = copy_from_user(vaddr, user_data, args->size);
+               mutex_lock(&dev->struct_mutex);
+               if (unwritten)
+                       return -EFAULT;
+       }
 
        drm_agp_chipset_flush(dev);
        return 0;