提交 aaefcd42 编写于 作者: D Dave Airlie

drm/radeon: deal with errors from framebuffer init path.

We've been getting occasional oops running a 32-bit kernel on a certain
system in our RHEL test hw. It appears that we fail to get sufficent ioremap
space for the framebuffer, and this leads to an oops.

This patch should fix the oops and leave a message in the logs we can
check for.

A future fix would probably to resize the console to a size that we can
ioremap.
Reviewed-by: NAlex Deucher <alexander.deucher@amd.com>
Signed-off-by: NDave Airlie <airlied@redhat.com>
上级 0be70439
...@@ -1078,15 +1078,21 @@ static const struct drm_framebuffer_funcs radeon_fb_funcs = { ...@@ -1078,15 +1078,21 @@ static const struct drm_framebuffer_funcs radeon_fb_funcs = {
.create_handle = radeon_user_framebuffer_create_handle, .create_handle = radeon_user_framebuffer_create_handle,
}; };
void int
radeon_framebuffer_init(struct drm_device *dev, radeon_framebuffer_init(struct drm_device *dev,
struct radeon_framebuffer *rfb, struct radeon_framebuffer *rfb,
struct drm_mode_fb_cmd2 *mode_cmd, struct drm_mode_fb_cmd2 *mode_cmd,
struct drm_gem_object *obj) struct drm_gem_object *obj)
{ {
int ret;
rfb->obj = obj; rfb->obj = obj;
drm_framebuffer_init(dev, &rfb->base, &radeon_fb_funcs); ret = drm_framebuffer_init(dev, &rfb->base, &radeon_fb_funcs);
if (ret) {
rfb->obj = NULL;
return ret;
}
drm_helper_mode_fill_fb_struct(&rfb->base, mode_cmd); drm_helper_mode_fill_fb_struct(&rfb->base, mode_cmd);
return 0;
} }
static struct drm_framebuffer * static struct drm_framebuffer *
...@@ -1096,6 +1102,7 @@ radeon_user_framebuffer_create(struct drm_device *dev, ...@@ -1096,6 +1102,7 @@ radeon_user_framebuffer_create(struct drm_device *dev,
{ {
struct drm_gem_object *obj; struct drm_gem_object *obj;
struct radeon_framebuffer *radeon_fb; struct radeon_framebuffer *radeon_fb;
int ret;
obj = drm_gem_object_lookup(dev, file_priv, mode_cmd->handles[0]); obj = drm_gem_object_lookup(dev, file_priv, mode_cmd->handles[0]);
if (obj == NULL) { if (obj == NULL) {
...@@ -1108,7 +1115,12 @@ radeon_user_framebuffer_create(struct drm_device *dev, ...@@ -1108,7 +1115,12 @@ radeon_user_framebuffer_create(struct drm_device *dev,
if (radeon_fb == NULL) if (radeon_fb == NULL)
return ERR_PTR(-ENOMEM); return ERR_PTR(-ENOMEM);
radeon_framebuffer_init(dev, radeon_fb, mode_cmd, obj); ret = radeon_framebuffer_init(dev, radeon_fb, mode_cmd, obj);
if (ret) {
kfree(radeon_fb);
drm_gem_object_unreference_unlocked(obj);
return NULL;
}
return &radeon_fb->base; return &radeon_fb->base;
} }
......
...@@ -209,6 +209,11 @@ static int radeonfb_create(struct radeon_fbdev *rfbdev, ...@@ -209,6 +209,11 @@ static int radeonfb_create(struct radeon_fbdev *rfbdev,
sizes->surface_depth); sizes->surface_depth);
ret = radeonfb_create_pinned_object(rfbdev, &mode_cmd, &gobj); ret = radeonfb_create_pinned_object(rfbdev, &mode_cmd, &gobj);
if (ret) {
DRM_ERROR("failed to create fbcon object %d\n", ret);
return ret;
}
rbo = gem_to_radeon_bo(gobj); rbo = gem_to_radeon_bo(gobj);
/* okay we have an object now allocate the framebuffer */ /* okay we have an object now allocate the framebuffer */
...@@ -220,7 +225,11 @@ static int radeonfb_create(struct radeon_fbdev *rfbdev, ...@@ -220,7 +225,11 @@ static int radeonfb_create(struct radeon_fbdev *rfbdev,
info->par = rfbdev; info->par = rfbdev;
radeon_framebuffer_init(rdev->ddev, &rfbdev->rfb, &mode_cmd, gobj); ret = radeon_framebuffer_init(rdev->ddev, &rfbdev->rfb, &mode_cmd, gobj);
if (ret) {
DRM_ERROR("failed to initalise framebuffer %d\n", ret);
goto out_unref;
}
fb = &rfbdev->rfb.base; fb = &rfbdev->rfb.base;
......
...@@ -649,7 +649,7 @@ extern void radeon_crtc_fb_gamma_set(struct drm_crtc *crtc, u16 red, u16 green, ...@@ -649,7 +649,7 @@ extern void radeon_crtc_fb_gamma_set(struct drm_crtc *crtc, u16 red, u16 green,
u16 blue, int regno); u16 blue, int regno);
extern void radeon_crtc_fb_gamma_get(struct drm_crtc *crtc, u16 *red, u16 *green, extern void radeon_crtc_fb_gamma_get(struct drm_crtc *crtc, u16 *red, u16 *green,
u16 *blue, int regno); u16 *blue, int regno);
void radeon_framebuffer_init(struct drm_device *dev, int radeon_framebuffer_init(struct drm_device *dev,
struct radeon_framebuffer *rfb, struct radeon_framebuffer *rfb,
struct drm_mode_fb_cmd2 *mode_cmd, struct drm_mode_fb_cmd2 *mode_cmd,
struct drm_gem_object *obj); struct drm_gem_object *obj);
......
Markdown is supported
0% .
You are about to add 0 people to the discussion. Proceed with caution.
先完成此消息的编辑!
想要评论请 注册