Skip to content

Commit

Permalink
---
Browse files Browse the repository at this point in the history
yaml
---
r: 218151
b: refs/heads/master
c: e133e73
h: refs/heads/master
i:
  218149: 3588f0c
  218147: 1ecac34
  218143: c93c8e0
v: v3
  • Loading branch information
Thomas Hellstrom authored and Dave Airlie committed Oct 6, 2010
1 parent aa91ad6 commit 39922ae
Show file tree
Hide file tree
Showing 5 changed files with 39 additions and 12 deletions.
2 changes: 1 addition & 1 deletion [refs]
Original file line number Diff line number Diff line change
@@ -1,2 +1,2 @@
---
refs/heads/master: 3a939a5ece3030e60c966a885c8e9bd329c4faf7
refs/heads/master: e133e7371231e49c3e7d626e2251cb6f7c3ca1ad
3 changes: 3 additions & 0 deletions trunk/drivers/gpu/drm/vmwgfx/vmwgfx_drv.h
Original file line number Diff line number Diff line change
Expand Up @@ -522,6 +522,9 @@ void vmw_kms_write_svga(struct vmw_private *vmw_priv,
int vmw_kms_update_layout_ioctl(struct drm_device *dev, void *data,
struct drm_file *file_priv);
void vmw_kms_idle_workqueues(struct vmw_master *vmaster);
bool vmw_kms_validate_mode_vram(struct vmw_private *dev_priv,
uint32_t pitch,
uint32_t height);
u32 vmw_get_vblank_counter(struct drm_device *dev, int crtc);

/**
Expand Down
7 changes: 7 additions & 0 deletions trunk/drivers/gpu/drm/vmwgfx/vmwgfx_fb.c
Original file line number Diff line number Diff line change
Expand Up @@ -144,6 +144,13 @@ static int vmw_fb_check_var(struct fb_var_screeninfo *var,
return -EINVAL;
}

if (!vmw_kms_validate_mode_vram(vmw_priv,
info->fix.line_length,
var->yoffset + var->yres)) {
DRM_ERROR("Requested geom can not fit in framebuffer\n");
return -EINVAL;
}

return 0;
}

Expand Down
11 changes: 9 additions & 2 deletions trunk/drivers/gpu/drm/vmwgfx/vmwgfx_kms.c
Original file line number Diff line number Diff line change
Expand Up @@ -838,7 +838,7 @@ static struct drm_framebuffer *vmw_kms_fb_create(struct drm_device *dev,
struct vmw_framebuffer *vfb = NULL;
struct vmw_surface *surface = NULL;
struct vmw_dma_buffer *bo = NULL;
unsigned int required_size;
u64 required_size;
int ret;

/**
Expand All @@ -848,7 +848,7 @@ static struct drm_framebuffer *vmw_kms_fb_create(struct drm_device *dev,
*/

required_size = mode_cmd->pitch * mode_cmd->height;
if (unlikely(required_size > dev_priv->vram_size)) {
if (unlikely(required_size > (u64) dev_priv->vram_size)) {
DRM_ERROR("VRAM size is too small for requested mode.\n");
return NULL;
}
Expand Down Expand Up @@ -1133,6 +1133,13 @@ int vmw_kms_update_layout_ioctl(struct drm_device *dev, void *data,
return ret;
}

bool vmw_kms_validate_mode_vram(struct vmw_private *dev_priv,
uint32_t pitch,
uint32_t height)
{
return ((u64) pitch * (u64) height) < (u64) dev_priv->vram_size;
}

u32 vmw_get_vblank_counter(struct drm_device *dev, int crtc)
{
return 0;
Expand Down
28 changes: 19 additions & 9 deletions trunk/drivers/gpu/drm/vmwgfx/vmwgfx_ldu.c
Original file line number Diff line number Diff line change
Expand Up @@ -427,7 +427,9 @@ static int vmw_ldu_connector_fill_modes(struct drm_connector *connector,
{
struct vmw_legacy_display_unit *ldu = vmw_connector_to_ldu(connector);
struct drm_device *dev = connector->dev;
struct vmw_private *dev_priv = vmw_priv(dev);
struct drm_display_mode *mode = NULL;
struct drm_display_mode *bmode;
struct drm_display_mode prefmode = { DRM_MODE("preferred",
DRM_MODE_TYPE_DRIVER | DRM_MODE_TYPE_PREFERRED,
0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0,
Expand All @@ -443,22 +445,30 @@ static int vmw_ldu_connector_fill_modes(struct drm_connector *connector,
mode->hdisplay = ldu->pref_width;
mode->vdisplay = ldu->pref_height;
mode->vrefresh = drm_mode_vrefresh(mode);
drm_mode_probed_add(connector, mode);
if (vmw_kms_validate_mode_vram(dev_priv, mode->hdisplay * 2,
mode->vdisplay)) {
drm_mode_probed_add(connector, mode);

if (ldu->pref_mode) {
list_del_init(&ldu->pref_mode->head);
drm_mode_destroy(dev, ldu->pref_mode);
}
if (ldu->pref_mode) {
list_del_init(&ldu->pref_mode->head);
drm_mode_destroy(dev, ldu->pref_mode);
}

ldu->pref_mode = mode;
ldu->pref_mode = mode;
}
}

for (i = 0; vmw_ldu_connector_builtin[i].type != 0; i++) {
if (vmw_ldu_connector_builtin[i].hdisplay > max_width ||
vmw_ldu_connector_builtin[i].vdisplay > max_height)
bmode = &vmw_ldu_connector_builtin[i];
if (bmode->hdisplay > max_width ||
bmode->vdisplay > max_height)
continue;

if (!vmw_kms_validate_mode_vram(dev_priv, bmode->hdisplay * 2,
bmode->vdisplay))
continue;

mode = drm_mode_duplicate(dev, &vmw_ldu_connector_builtin[i]);
mode = drm_mode_duplicate(dev, bmode);
if (!mode)
return 0;
mode->vrefresh = drm_mode_vrefresh(mode);
Expand Down

0 comments on commit 39922ae

Please sign in to comment.