drm: fix up fb resize again
authorDave Airlie <airlied@linux.ie>
Fri, 6 Jun 2008 06:24:27 +0000 (16:24 +1000)
committerDave Airlie <airlied@linux.ie>
Fri, 6 Jun 2008 06:24:27 +0000 (16:24 +1000)
linux-core/drm_crtc.c
linux-core/drm_crtc.h
linux-core/drm_crtc_helper.c
linux-core/intel_display.c

index d49834b..e1b371c 100644 (file)
@@ -2055,25 +2055,10 @@ int drm_mode_replacefb(struct drm_device *dev,
                goto out;
        }
 
-       fb->width = r->width;
-       fb->height = r->height;
-       fb->pitch = r->pitch;
-       fb->bits_per_pixel = r->bpp;
-       fb->depth = r->depth;
-       fb->mm_handle = r->handle;
-
        if (dev->mode_config.funcs->resize_fb)
-         dev->mode_config.funcs->resize_fb(dev, fb);
+               ret = dev->mode_config.funcs->resize_fb(dev, file_priv, fb, r);
        else
-         ret = -EINVAL;
-#if 0
-       /* find all crtcs connected to this fb */
-       list_for_each_entry(crtc, &dev->mode_config.crtc_list, head) {
-               if (crtc->fb->base.id == r->buffer_id) {
-                       crtc->funcs->mode_set_base(crtc, crtc->x, crtc->y);
-               }
-       }
-#endif
+               ret = -EINVAL;
 out:
        mutex_unlock(&dev->mode_config.mutex);
        return ret;
index 043b4a5..5f5f195 100644 (file)
@@ -522,9 +522,9 @@ struct drm_mode_set {
  * the CRTC<->connector mappings as needed and update its view of the screen.
  */
 struct drm_mode_config_funcs {
-       bool (*resize_fb)(struct drm_device *dev, struct drm_framebuffer *fb);
+       int (*resize_fb)(struct drm_device *dev, struct drm_file *file_priv, struct drm_framebuffer *fb, struct drm_mode_fb_cmd *mode_cmd);
        struct drm_framebuffer *(*fb_create)(struct drm_device *dev, struct drm_file *file_priv, struct drm_mode_fb_cmd *mode_cmd);
-       void (*fb_changed)(struct drm_device *dev);
+       int (*fb_changed)(struct drm_device *dev);
 };
 
 struct drm_mode_group {
index 777820d..bfddab9 100644 (file)
@@ -758,3 +758,4 @@ out_err:
        return ret;
 }
 EXPORT_SYMBOL(drm_get_buffer_object);
+
index 0081b5b..0a2854a 100644 (file)
@@ -1517,8 +1517,38 @@ struct drm_framebuffer *intel_user_framebuffer_create(struct drm_device *dev,
        return &intel_fb->base;
 }
 
+static int intel_insert_new_fb(struct drm_device *dev, struct drm_file *file_priv,
+                               struct drm_framebuffer *fb, struct drm_mode_fb_cmd *mode_cmd)
+{
+       struct intel_framebuffer *intel_fb;
+       struct drm_buffer_object *bo;
+       struct drm_crtc *crtc;
+
+       intel_fb = to_intel_framebuffer(fb);
+
+       mutex_lock(&dev->struct_mutex);
+       bo = drm_lookup_buffer_object(file_priv, mode_cmd->handle, 0);
+       mutex_unlock(&dev->struct_mutex);
+       
+       if (!bo)
+               return -EINVAL;
+       drm_helper_mode_fill_fb_struct(fb, mode_cmd);
+       
+       drm_bo_usage_deref_unlocked(&intel_fb->bo);
+
+       intel_fb->bo = bo;
+
+       list_for_each_entry(crtc, &dev->mode_config.crtc_list, head) {
+               if (crtc->fb == fb) {
+                       struct drm_crtc_helper_funcs *crtc_funcs = crtc->helper_private;
+                       crtc_funcs->mode_set_base(crtc, crtc->x, crtc->y);
+               }
+       }
+       return 0;
+}
+
 static const struct drm_mode_config_funcs intel_mode_funcs = {
-       .resize_fb = NULL,
+       .resize_fb = intel_insert_new_fb,
        .fb_create = intel_user_framebuffer_create,
        .fb_changed = intelfb_probe,
 };