aboutsummaryrefslogtreecommitdiffstats
path: root/drivers/gpu/drm/mgag200
diff options
context:
space:
mode:
Diffstat (limited to 'drivers/gpu/drm/mgag200')
-rw-r--r--drivers/gpu/drm/mgag200/Kconfig2
-rw-r--r--drivers/gpu/drm/mgag200/mgag200_cursor.c183
-rw-r--r--drivers/gpu/drm/mgag200/mgag200_drv.c13
-rw-r--r--drivers/gpu/drm/mgag200/mgag200_drv.h75
-rw-r--r--drivers/gpu/drm/mgag200/mgag200_fb.c59
-rw-r--r--drivers/gpu/drm/mgag200/mgag200_main.c91
-rw-r--r--drivers/gpu/drm/mgag200/mgag200_mode.c59
-rw-r--r--drivers/gpu/drm/mgag200/mgag200_ttm.c301
8 files changed, 179 insertions, 604 deletions
diff --git a/drivers/gpu/drm/mgag200/Kconfig b/drivers/gpu/drm/mgag200/Kconfig
index 91f3579546d0..76fee0fbdcae 100644
--- a/drivers/gpu/drm/mgag200/Kconfig
+++ b/drivers/gpu/drm/mgag200/Kconfig
@@ -3,7 +3,7 @@ config DRM_MGAG200
tristate "Kernel modesetting driver for MGA G200 server engines"
depends on DRM && PCI && MMU
select DRM_KMS_HELPER
- select DRM_TTM
+ select DRM_VRAM_HELPER
help
This is a KMS driver for the MGA G200 server chips, it
does not support the original MGA G200 or any of the desktop
diff --git a/drivers/gpu/drm/mgag200/mgag200_cursor.c b/drivers/gpu/drm/mgag200/mgag200_cursor.c
index 853387b0fa88..f0c61a92351c 100644
--- a/drivers/gpu/drm/mgag200/mgag200_cursor.c
+++ b/drivers/gpu/drm/mgag200/mgag200_cursor.c
@@ -19,10 +19,9 @@ static void mga_hide_cursor(struct mga_device *mdev)
{
WREG8(MGA_CURPOSXL, 0);
WREG8(MGA_CURPOSXH, 0);
- if (mdev->cursor.pixels_1->pin_count)
- mgag200_bo_unpin(mdev->cursor.pixels_1);
- if (mdev->cursor.pixels_2->pin_count)
- mgag200_bo_unpin(mdev->cursor.pixels_2);
+ if (mdev->cursor.pixels_current)
+ drm_gem_vram_unpin(mdev->cursor.pixels_current);
+ mdev->cursor.pixels_current = NULL;
}
int mga_crtc_cursor_set(struct drm_crtc *crtc,
@@ -33,13 +32,14 @@ int mga_crtc_cursor_set(struct drm_crtc *crtc,
{
struct drm_device *dev = crtc->dev;
struct mga_device *mdev = (struct mga_device *)dev->dev_private;
- struct mgag200_bo *pixels_1 = mdev->cursor.pixels_1;
- struct mgag200_bo *pixels_2 = mdev->cursor.pixels_2;
- struct mgag200_bo *pixels_current = mdev->cursor.pixels_current;
- struct mgag200_bo *pixels_prev = mdev->cursor.pixels_prev;
+ struct drm_gem_vram_object *pixels_1 = mdev->cursor.pixels_1;
+ struct drm_gem_vram_object *pixels_2 = mdev->cursor.pixels_2;
+ struct drm_gem_vram_object *pixels_current = mdev->cursor.pixels_current;
+ struct drm_gem_vram_object *pixels_next;
struct drm_gem_object *obj;
- struct mgag200_bo *bo = NULL;
+ struct drm_gem_vram_object *gbo = NULL;
int ret = 0;
+ u8 *src, *dst;
unsigned int i, row, col;
uint32_t colour_set[16];
uint32_t *next_space = &colour_set[0];
@@ -47,7 +47,8 @@ int mga_crtc_cursor_set(struct drm_crtc *crtc,
uint32_t this_colour;
bool found = false;
int colour_count = 0;
- u64 gpu_addr;
+ s64 gpu_addr;
+ u64 dst_gpu;
u8 reg_index;
u8 this_row[48];
@@ -57,73 +58,71 @@ int mga_crtc_cursor_set(struct drm_crtc *crtc,
return -ENOTSUPP; /* Didn't allocate space for cursors */
}
- if ((width != 64 || height != 64) && handle) {
- WREG8(MGA_CURPOSXL, 0);
- WREG8(MGA_CURPOSXH, 0);
- return -EINVAL;
+ if (WARN_ON(pixels_current &&
+ pixels_1 != pixels_current &&
+ pixels_2 != pixels_current)) {
+ return -ENOTSUPP; /* inconsistent state */
}
- BUG_ON(pixels_1 != pixels_current && pixels_1 != pixels_prev);
- BUG_ON(pixels_2 != pixels_current && pixels_2 != pixels_prev);
- BUG_ON(pixels_current == pixels_prev);
-
if (!handle || !file_priv) {
mga_hide_cursor(mdev);
return 0;
}
- obj = drm_gem_object_lookup(file_priv, handle);
- if (!obj)
- return -ENOENT;
-
- ret = mgag200_bo_reserve(pixels_1, true);
- if (ret) {
+ if (width != 64 || height != 64) {
WREG8(MGA_CURPOSXL, 0);
WREG8(MGA_CURPOSXH, 0);
- goto out_unref;
- }
- ret = mgag200_bo_reserve(pixels_2, true);
- if (ret) {
- WREG8(MGA_CURPOSXL, 0);
- WREG8(MGA_CURPOSXH, 0);
- mgag200_bo_unreserve(pixels_1);
- goto out_unreserve1;
+ return -EINVAL;
}
- /* Move cursor buffers into VRAM if they aren't already */
- if (!pixels_1->pin_count) {
- ret = mgag200_bo_pin(pixels_1, TTM_PL_FLAG_VRAM,
- &mdev->cursor.pixels_1_gpu_addr);
- if (ret)
- goto out1;
+ if (pixels_current == pixels_1)
+ pixels_next = pixels_2;
+ else
+ pixels_next = pixels_1;
+
+ obj = drm_gem_object_lookup(file_priv, handle);
+ if (!obj)
+ return -ENOENT;
+ gbo = drm_gem_vram_of_gem(obj);
+ ret = drm_gem_vram_pin(gbo, 0);
+ if (ret) {
+ dev_err(&dev->pdev->dev, "failed to lock user bo\n");
+ goto err_drm_gem_object_put_unlocked;
}
- if (!pixels_2->pin_count) {
- ret = mgag200_bo_pin(pixels_2, TTM_PL_FLAG_VRAM,
- &mdev->cursor.pixels_2_gpu_addr);
- if (ret) {
- mgag200_bo_unpin(pixels_1);
- goto out1;
- }
+ src = drm_gem_vram_kmap(gbo, true, NULL);
+ if (IS_ERR(src)) {
+ ret = PTR_ERR(src);
+ dev_err(&dev->pdev->dev,
+ "failed to kmap user buffer updates\n");
+ goto err_drm_gem_vram_unpin_src;
}
- bo = gem_to_mga_bo(obj);
- ret = mgag200_bo_reserve(bo, true);
- if (ret) {
- dev_err(&dev->pdev->dev, "failed to reserve user bo\n");
- goto out1;
+ /* Pin and map up-coming buffer to write colour indices */
+ ret = drm_gem_vram_pin(pixels_next, 0);
+ if (ret)
+ dev_err(&dev->pdev->dev,
+ "failed to pin cursor buffer: %d\n", ret);
+ goto err_drm_gem_vram_kunmap_src;
+ dst = drm_gem_vram_kmap(pixels_next, true, NULL);
+ if (IS_ERR(dst)) {
+ ret = PTR_ERR(dst);
+ dev_err(&dev->pdev->dev,
+ "failed to kmap cursor updates: %d\n", ret);
+ goto err_drm_gem_vram_unpin_dst;
}
- if (!bo->kmap.virtual) {
- ret = ttm_bo_kmap(&bo->bo, 0, bo->bo.num_pages, &bo->kmap);
- if (ret) {
- dev_err(&dev->pdev->dev, "failed to kmap user buffer updates\n");
- goto out2;
- }
+ gpu_addr = drm_gem_vram_offset(pixels_2);
+ if (gpu_addr < 0) {
+ ret = (int)gpu_addr;
+ dev_err(&dev->pdev->dev,
+ "failed to get cursor scanout address: %d\n", ret);
+ goto err_drm_gem_vram_kunmap_dst;
}
+ dst_gpu = (u64)gpu_addr;
memset(&colour_set[0], 0, sizeof(uint32_t)*16);
/* width*height*4 = 16384 */
for (i = 0; i < 16384; i += 4) {
- this_colour = ioread32(bo->kmap.virtual + i);
+ this_colour = ioread32(src + i);
/* No transparency */
if (this_colour>>24 != 0xff &&
this_colour>>24 != 0x0) {
@@ -133,7 +132,7 @@ int mga_crtc_cursor_set(struct drm_crtc *crtc,
warn_transparent = false; /* Only tell the user once. */
}
ret = -EINVAL;
- goto out3;
+ goto err_drm_gem_vram_kunmap_dst;
}
/* Don't need to store transparent pixels as colours */
if (this_colour>>24 == 0x0)
@@ -155,7 +154,7 @@ int mga_crtc_cursor_set(struct drm_crtc *crtc,
warn_palette = false; /* Only tell the user once. */
}
ret = -EINVAL;
- goto out3;
+ goto err_drm_gem_vram_kunmap_dst;
}
*next_space = this_colour;
next_space++;
@@ -174,22 +173,11 @@ int mga_crtc_cursor_set(struct drm_crtc *crtc,
BUG_ON((colour_set[i]>>24 & 0xff) != 0xff);
}
- /* Map up-coming buffer to write colour indices */
- if (!pixels_prev->kmap.virtual) {
- ret = ttm_bo_kmap(&pixels_prev->bo, 0,
- pixels_prev->bo.num_pages,
- &pixels_prev->kmap);
- if (ret) {
- dev_err(&dev->pdev->dev, "failed to kmap cursor updates\n");
- goto out3;
- }
- }
-
/* now write colour indices into hardware cursor buffer */
for (row = 0; row < 64; row++) {
memset(&this_row[0], 0, 48);
for (col = 0; col < 64; col++) {
- this_colour = ioread32(bo->kmap.virtual + 4*(col + 64*row));
+ this_colour = ioread32(src + 4*(col + 64*row));
/* write transparent pixels */
if (this_colour>>24 == 0x0) {
this_row[47 - col/8] |= 0x80>>(col%8);
@@ -207,46 +195,39 @@ int mga_crtc_cursor_set(struct drm_crtc *crtc,
}
}
}
- memcpy_toio(pixels_prev->kmap.virtual + row*48, &this_row[0], 48);
+ memcpy_toio(dst + row*48, &this_row[0], 48);
}
/* Program gpu address of cursor buffer */
- if (pixels_prev == pixels_1)
- gpu_addr = mdev->cursor.pixels_1_gpu_addr;
- else
- gpu_addr = mdev->cursor.pixels_2_gpu_addr;
- WREG_DAC(MGA1064_CURSOR_BASE_ADR_LOW, (u8)((gpu_addr>>10) & 0xff));
- WREG_DAC(MGA1064_CURSOR_BASE_ADR_HI, (u8)((gpu_addr>>18) & 0x3f));
+ WREG_DAC(MGA1064_CURSOR_BASE_ADR_LOW, (u8)((dst_gpu>>10) & 0xff));
+ WREG_DAC(MGA1064_CURSOR_BASE_ADR_HI, (u8)((dst_gpu>>18) & 0x3f));
/* Adjust cursor control register to turn on the cursor */
WREG_DAC(MGA1064_CURSOR_CTL, 4); /* 16-colour palletized cursor mode */
- /* Now swap internal buffer pointers */
- if (mdev->cursor.pixels_1 == mdev->cursor.pixels_prev) {
- mdev->cursor.pixels_prev = mdev->cursor.pixels_2;
- mdev->cursor.pixels_current = mdev->cursor.pixels_1;
- } else if (mdev->cursor.pixels_1 == mdev->cursor.pixels_current) {
- mdev->cursor.pixels_prev = mdev->cursor.pixels_1;
- mdev->cursor.pixels_current = mdev->cursor.pixels_2;
- } else {
- BUG();
- }
- ret = 0;
+ /* Now update internal buffer pointers */
+ if (pixels_current)
+ drm_gem_vram_unpin(pixels_current);
+ mdev->cursor.pixels_current = pixels_next;
- ttm_bo_kunmap(&pixels_prev->kmap);
- out3:
- ttm_bo_kunmap(&bo->kmap);
- out2:
- mgag200_bo_unreserve(bo);
- out1:
- if (ret)
- mga_hide_cursor(mdev);
- mgag200_bo_unreserve(pixels_1);
-out_unreserve1:
- mgag200_bo_unreserve(pixels_2);
-out_unref:
+ drm_gem_vram_kunmap(pixels_next);
+ drm_gem_vram_unpin(pixels_next);
+ drm_gem_vram_kunmap(gbo);
+ drm_gem_vram_unpin(gbo);
drm_gem_object_put_unlocked(obj);
+ return 0;
+
+err_drm_gem_vram_kunmap_dst:
+ drm_gem_vram_kunmap(pixels_next);
+err_drm_gem_vram_unpin_dst:
+ drm_gem_vram_unpin(pixels_next);
+err_drm_gem_vram_kunmap_src:
+ drm_gem_vram_kunmap(gbo);
+err_drm_gem_vram_unpin_src:
+ drm_gem_vram_unpin(gbo);
+err_drm_gem_object_put_unlocked:
+ drm_gem_object_put_unlocked(obj);
return ret;
}
diff --git a/drivers/gpu/drm/mgag200/mgag200_drv.c b/drivers/gpu/drm/mgag200/mgag200_drv.c
index efd2145bc0a2..aafa1cb31f50 100644
--- a/drivers/gpu/drm/mgag200/mgag200_drv.c
+++ b/drivers/gpu/drm/mgag200/mgag200_drv.c
@@ -56,13 +56,7 @@ static void mga_pci_remove(struct pci_dev *pdev)
static const struct file_operations mgag200_driver_fops = {
.owner = THIS_MODULE,
- .open = drm_open,
- .release = drm_release,
- .unlocked_ioctl = drm_ioctl,
- .mmap = mgag200_mmap,
- .poll = drm_poll,
- .compat_ioctl = drm_compat_ioctl,
- .read = drm_read,
+ DRM_VRAM_MM_FILE_OPERATIONS
};
static struct drm_driver driver = {
@@ -76,10 +70,7 @@ static struct drm_driver driver = {
.major = DRIVER_MAJOR,
.minor = DRIVER_MINOR,
.patchlevel = DRIVER_PATCHLEVEL,
-
- .gem_free_object_unlocked = mgag200_gem_free_object,
- .dumb_create = mgag200_dumb_create,
- .dumb_map_offset = mgag200_dumb_mmap_offset,
+ DRM_GEM_VRAM_DRIVER
};
static struct pci_driver mgag200_pci_driver = {
diff --git a/drivers/gpu/drm/mgag200/mgag200_drv.h b/drivers/gpu/drm/mgag200/mgag200_drv.h
index 8506e6d62b63..c47671ce6c48 100644
--- a/drivers/gpu/drm/mgag200/mgag200_drv.h
+++ b/drivers/gpu/drm/mgag200/mgag200_drv.h
@@ -1,7 +1,7 @@
/* SPDX-License-Identifier: GPL-2.0-only */
/*
* Copyright 2010 Matt Turner.
- * Copyright 2012 Red Hat
+ * Copyright 2012 Red Hat
*
* Authors: Matthew Garrett
* Matt Turner
@@ -14,13 +14,11 @@
#include <drm/drm_encoder.h>
#include <drm/drm_fb_helper.h>
-#include <drm/ttm/ttm_bo_api.h>
-#include <drm/ttm/ttm_bo_driver.h>
-#include <drm/ttm/ttm_placement.h>
-#include <drm/ttm/ttm_memory.h>
-#include <drm/ttm/ttm_module.h>
#include <drm/drm_gem.h>
+#include <drm/drm_gem_vram_helper.h>
+
+#include <drm/drm_vram_mm_helper.h>
#include <linux/i2c.h>
#include <linux/i2c-algo-bit.h>
@@ -114,7 +112,6 @@ struct mga_fbdev {
struct mga_framebuffer mfb;
void *sysram;
int size;
- struct ttm_bo_kmap_obj mapping;
int x1, y1, x2, y2; /* dirty rect */
spinlock_t dirty_lock;
};
@@ -156,13 +153,10 @@ struct mga_cursor {
If either of these is NULL, then don't do hardware cursors, and
fall back to software.
*/
- struct mgag200_bo *pixels_1;
- struct mgag200_bo *pixels_2;
- u64 pixels_1_gpu_addr, pixels_2_gpu_addr;
+ struct drm_gem_vram_object *pixels_1;
+ struct drm_gem_vram_object *pixels_2;
/* The currently displayed icon, this points to one of pixels_1, or pixels_2 */
- struct mgag200_bo *pixels_current;
- /* The previously displayed icon */
- struct mgag200_bo *pixels_prev;
+ struct drm_gem_vram_object *pixels_current;
};
struct mga_mc {
@@ -208,31 +202,10 @@ struct mga_device {
int fb_mtrr;
- struct {
- struct ttm_bo_device bdev;
- } ttm;
-
/* SE model number stored in reg 0x1e24 */
u32 unique_rev_id;
};
-
-struct mgag200_bo {
- struct ttm_buffer_object bo;
- struct ttm_placement placement;
- struct ttm_bo_kmap_obj kmap;
- struct drm_gem_object gem;
- struct ttm_place placements[3];
- int pin_count;
-};
-#define gem_to_mga_bo(gobj) container_of((gobj), struct mgag200_bo, gem)
-
-static inline struct mgag200_bo *
-mgag200_bo(struct ttm_buffer_object *bo)
-{
- return container_of(bo, struct mgag200_bo, bo);
-}
-
/* mgag200_mode.c */
int mgag200_modeset_init(struct mga_device *mdev);
void mgag200_modeset_fini(struct mga_device *mdev);
@@ -256,45 +229,15 @@ int mgag200_gem_create(struct drm_device *dev,
int mgag200_dumb_create(struct drm_file *file,
struct drm_device *dev,
struct drm_mode_create_dumb *args);
-void mgag200_gem_free_object(struct drm_gem_object *obj);
-int
-mgag200_dumb_mmap_offset(struct drm_file *file,
- struct drm_device *dev,
- uint32_t handle,
- uint64_t *offset);
+
/* mgag200_i2c.c */
struct mga_i2c_chan *mgag200_i2c_create(struct drm_device *dev);
void mgag200_i2c_destroy(struct mga_i2c_chan *i2c);
-void mgag200_ttm_placement(struct mgag200_bo *bo, int domain);
-
-static inline int mgag200_bo_reserve(struct mgag200_bo *bo, bool no_wait)
-{
- int ret;
-
- ret = ttm_bo_reserve(&bo->bo, true, no_wait, NULL);
- if (ret) {
- if (ret != -ERESTARTSYS && ret != -EBUSY)
- DRM_ERROR("reserve failed %p\n", bo);
- return ret;
- }
- return 0;
-}
-
-static inline void mgag200_bo_unreserve(struct mgag200_bo *bo)
-{
- ttm_bo_unreserve(&bo->bo);
-}
-
-int mgag200_bo_create(struct drm_device *dev, int size, int align,
- uint32_t flags, struct mgag200_bo **pastbo);
int mgag200_mm_init(struct mga_device *mdev);
void mgag200_mm_fini(struct mga_device *mdev);
int mgag200_mmap(struct file *filp, struct vm_area_struct *vma);
-int mgag200_bo_pin(struct mgag200_bo *bo, u32 pl_flag, u64 *gpu_addr);
-int mgag200_bo_unpin(struct mgag200_bo *bo);
-int mgag200_bo_push_sysram(struct mgag200_bo *bo);
- /* mgag200_cursor.c */
+
int mga_crtc_cursor_set(struct drm_crtc *crtc, struct drm_file *file_priv,
uint32_t handle, uint32_t width, uint32_t height);
int mga_crtc_cursor_move(struct drm_crtc *crtc, int x, int y);
diff --git a/drivers/gpu/drm/mgag200/mgag200_fb.c b/drivers/gpu/drm/mgag200/mgag200_fb.c
index c4d1dcc5afde..8adb33228732 100644
--- a/drivers/gpu/drm/mgag200/mgag200_fb.c
+++ b/drivers/gpu/drm/mgag200/mgag200_fb.c
@@ -20,29 +20,31 @@ static void mga_dirty_update(struct mga_fbdev *mfbdev,
{
int i;
struct drm_gem_object *obj;
- struct mgag200_bo *bo;
+ struct drm_gem_vram_object *gbo;
int src_offset, dst_offset;
int bpp = mfbdev->mfb.base.format->cpp[0];
- int ret = -EBUSY;
+ int ret;
+ u8 *dst;
bool unmap = false;
bool store_for_later = false;
int x2, y2;
unsigned long flags;
obj = mfbdev->mfb.obj;
- bo = gem_to_mga_bo(obj);
-
- /*
- * try and reserve the BO, if we fail with busy
- * then the BO is being moved and we should
- * store up the damage until later.
- */
- if (drm_can_sleep())
- ret = mgag200_bo_reserve(bo, true);
- if (ret) {
- if (ret != -EBUSY)
- return;
-
+ gbo = drm_gem_vram_of_gem(obj);
+
+ if (drm_can_sleep()) {
+ /* We pin the BO so it won't be moved during the
+ * update. The actual location, video RAM or system
+ * memory, is not important.
+ */
+ ret = drm_gem_vram_pin(gbo, 0);
+ if (ret) {
+ if (ret != -EBUSY)
+ return;
+ store_for_later = true;
+ }
+ } else {
store_for_later = true;
}
@@ -72,25 +74,32 @@ static void mga_dirty_update(struct mga_fbdev *mfbdev,
mfbdev->x2 = mfbdev->y2 = 0;
spin_unlock_irqrestore(&mfbdev->dirty_lock, flags);
- if (!bo->kmap.virtual) {
- ret = ttm_bo_kmap(&bo->bo, 0, bo->bo.num_pages, &bo->kmap);
- if (ret) {
+ dst = drm_gem_vram_kmap(gbo, false, NULL);
+ if (IS_ERR(dst)) {
+ DRM_ERROR("failed to kmap fb updates\n");
+ goto out;
+ } else if (!dst) {
+ dst = drm_gem_vram_kmap(gbo, true, NULL);
+ if (IS_ERR(dst)) {
DRM_ERROR("failed to kmap fb updates\n");
- mgag200_bo_unreserve(bo);
- return;
+ goto out;
}
unmap = true;
}
+
for (i = y; i <= y2; i++) {
/* assume equal stride for now */
- src_offset = dst_offset = i * mfbdev->mfb.base.pitches[0] + (x * bpp);
- memcpy_toio(bo->kmap.virtual + src_offset, mfbdev->sysram + src_offset, (x2 - x + 1) * bpp);
-
+ src_offset = dst_offset =
+ i * mfbdev->mfb.base.pitches[0] + (x * bpp);
+ memcpy_toio(dst + dst_offset, mfbdev->sysram + src_offset,
+ (x2 - x + 1) * bpp);
}
+
if (unmap)
- ttm_bo_kunmap(&bo->kmap);
+ drm_gem_vram_kunmap(gbo);
- mgag200_bo_unreserve(bo);
+out:
+ drm_gem_vram_unpin(gbo);
}
static void mga_fillrect(struct fb_info *info,
diff --git a/drivers/gpu/drm/mgag200/mgag200_main.c b/drivers/gpu/drm/mgag200/mgag200_main.c
index 5333bd41a36f..dd61ccc5af5c 100644
--- a/drivers/gpu/drm/mgag200/mgag200_main.c
+++ b/drivers/gpu/drm/mgag200/mgag200_main.c
@@ -227,19 +227,19 @@ int mgag200_driver_load(struct drm_device *dev, unsigned long flags)
}
/* Make small buffers to store a hardware cursor (double buffered icon updates) */
- mgag200_bo_create(dev, roundup(48*64, PAGE_SIZE), 0, 0,
- &mdev->cursor.pixels_1);
- mgag200_bo_create(dev, roundup(48*64, PAGE_SIZE), 0, 0,
- &mdev->cursor.pixels_2);
- if (!mdev->cursor.pixels_2 || !mdev->cursor.pixels_1) {
+ mdev->cursor.pixels_1 = drm_gem_vram_create(dev, &dev->vram_mm->bdev,
+ roundup(48*64, PAGE_SIZE),
+ 0, 0);
+ mdev->cursor.pixels_2 = drm_gem_vram_create(dev, &dev->vram_mm->bdev,
+ roundup(48*64, PAGE_SIZE),
+ 0, 0);
+ if (IS_ERR(mdev->cursor.pixels_2) || IS_ERR(mdev->cursor.pixels_1)) {
mdev->cursor.pixels_1 = NULL;
mdev->cursor.pixels_2 = NULL;
dev_warn(&dev->pdev->dev,
"Could not allocate space for cursors. Not doing hardware cursors.\n");
- } else {
- mdev->cursor.pixels_current = mdev->cursor.pixels_1;
- mdev->cursor.pixels_prev = mdev->cursor.pixels_2;
}
+ mdev->cursor.pixels_current = NULL;
return 0;
@@ -269,7 +269,7 @@ int mgag200_gem_create(struct drm_device *dev,
u32 size, bool iskernel,
struct drm_gem_object **obj)
{
- struct mgag200_bo *astbo;
+ struct drm_gem_vram_object *gbo;
int ret;
*obj = NULL;
@@ -278,78 +278,13 @@ int mgag200_gem_create(struct drm_device *dev,
if (size == 0)
return -EINVAL;
- ret = mgag200_bo_create(dev, size, 0, 0, &astbo);
- if (ret) {
+ gbo = drm_gem_vram_create(dev, &dev->vram_mm->bdev, size, 0, false);
+ if (IS_ERR(gbo)) {
+ ret = PTR_ERR(gbo);
if (ret != -ERESTARTSYS)
DRM_ERROR("failed to allocate GEM object\n");
return ret;
}
- *obj = &astbo->gem;
- return 0;
-}
-
-int mgag200_dumb_create(struct drm_file *file,
- struct drm_device *dev,
- struct drm_mode_create_dumb *args)
-{
- int ret;
- struct drm_gem_object *gobj;
- u32 handle;
-
- args->pitch = args->width * ((args->bpp + 7) / 8);
- args->size = args->pitch * args->height;
-
- ret = mgag200_gem_create(dev, args->size, false,
- &gobj);
- if (ret)
- return ret;
-
- ret = drm_gem_handle_create(file, gobj, &handle);
- drm_gem_object_put_unlocked(gobj);
- if (ret)
- return ret;
-
- args->handle = handle;
- return 0;
-}
-
-static void mgag200_bo_unref(struct mgag200_bo **bo)
-{
- if ((*bo) == NULL)
- return;
- ttm_bo_put(&((*bo)->bo));
- *bo = NULL;
-}
-
-void mgag200_gem_free_object(struct drm_gem_object *obj)
-{
- struct mgag200_bo *mgag200_bo = gem_to_mga_bo(obj);
-
- mgag200_bo_unref(&mgag200_bo);
-}
-
-
-static inline u64 mgag200_bo_mmap_offset(struct mgag200_bo *bo)
-{
- return drm_vma_node_offset_addr(&bo->bo.vma_node);
-}
-
-int
-mgag200_dumb_mmap_offset(struct drm_file *file,
- struct drm_device *dev,
- uint32_t handle,
- uint64_t *offset)
-{
- struct drm_gem_object *obj;
- struct mgag200_bo *bo;
-
- obj = drm_gem_object_lookup(file, handle);
- if (obj == NULL)
- return -ENOENT;
-
- bo = gem_to_mga_bo(obj);
- *offset = mgag200_bo_mmap_offset(bo);
-
- drm_gem_object_put_unlocked(obj);
+ *obj = &gbo->gem;
return 0;
}
diff --git a/drivers/gpu/drm/mgag200/mgag200_mode.c b/drivers/gpu/drm/mgag200/mgag200_mode.c
index 210a19354f1c..a25054015e8c 100644
--- a/drivers/gpu/drm/mgag200/mgag200_mode.c
+++ b/drivers/gpu/drm/mgag200/mgag200_mode.c
@@ -855,8 +855,6 @@ static void mga_set_start_address(struct drm_crtc *crtc, unsigned offset)
WREG_ECRT(0x0, ((u8)(addr >> 16) & 0xf) | crtcext0);
}
-
-/* ast is different - we will force move buffers out of VRAM */
static int mga_crtc_do_set_base(struct drm_crtc *crtc,
struct drm_framebuffer *fb,
int x, int y, int atomic)
@@ -864,48 +862,51 @@ static int mga_crtc_do_set_base(struct drm_crtc *crtc,
struct mga_device *mdev = crtc->dev->dev_private;
struct drm_gem_object *obj;
struct mga_framebuffer *mga_fb;
- struct mgag200_bo *bo;
+ struct drm_gem_vram_object *gbo;
int ret;
- u64 gpu_addr;
+ s64 gpu_addr;
+ void *base;
- /* push the previous fb to system ram */
if (!atomic && fb) {
mga_fb = to_mga_framebuffer(fb);
obj = mga_fb->obj;
- bo = gem_to_mga_bo(obj);
- ret = mgag200_bo_reserve(bo, false);
- if (ret)
- return ret;
- mgag200_bo_push_sysram(bo);
- mgag200_bo_unreserve(bo);
+ gbo = drm_gem_vram_of_gem(obj);
+
+ /* unmap if console */
+ if (&mdev->mfbdev->mfb == mga_fb)
+ drm_gem_vram_kunmap(gbo);
+ drm_gem_vram_unpin(gbo);
}
mga_fb = to_mga_framebuffer(crtc->primary->fb);
obj = mga_fb->obj;
- bo = gem_to_mga_bo(obj);
+ gbo = drm_gem_vram_of_gem(obj);
- ret = mgag200_bo_reserve(bo, false);
+ ret = drm_gem_vram_pin(gbo, DRM_GEM_VRAM_PL_FLAG_VRAM);
if (ret)
return ret;
-
- ret = mgag200_bo_pin(bo, TTM_PL_FLAG_VRAM, &gpu_addr);
- if (ret) {
- mgag200_bo_unreserve(bo);
- return ret;
+ gpu_addr = drm_gem_vram_offset(gbo);
+ if (gpu_addr < 0) {
+ ret = (int)gpu_addr;
+ goto err_drm_gem_vram_unpin;
}
if (&mdev->mfbdev->mfb == mga_fb) {
/* if pushing console in kmap it */
- ret = ttm_bo_kmap(&bo->bo, 0, bo->bo.num_pages, &bo->kmap);
- if (ret)
+ base = drm_gem_vram_kmap(gbo, true, NULL);
+ if (IS_ERR(base)) {
+ ret = PTR_ERR(base);
DRM_ERROR("failed to kmap fbcon\n");
-
+ }
}
- mgag200_bo_unreserve(bo);
mga_set_start_address(crtc, (u32)gpu_addr);
return 0;
+
+err_drm_gem_vram_unpin:
+ drm_gem_vram_unpin(gbo);
+ return ret;
}
static int mga_crtc_mode_set_base(struct drm_crtc *crtc, int x, int y,
@@ -1419,18 +1420,18 @@ static void mga_crtc_destroy(struct drm_crtc *crtc)
static void mga_crtc_disable(struct drm_crtc *crtc)
{
- int ret;
DRM_DEBUG_KMS("\n");
mga_crtc_dpms(crtc, DRM_MODE_DPMS_OFF);
if (crtc->primary->fb) {
+ struct mga_device *mdev = crtc->dev->dev_private;
struct mga_framebuffer *mga_fb = to_mga_framebuffer(crtc->primary->fb);
struct drm_gem_object *obj = mga_fb->obj;
- struct mgag200_bo *bo = gem_to_mga_bo(obj);
- ret = mgag200_bo_reserve(bo, false);
- if (ret)
- return;
- mgag200_bo_push_sysram(bo);
- mgag200_bo_unreserve(bo);
+ struct drm_gem_vram_object *gbo = drm_gem_vram_of_gem(obj);
+
+ /* unmap if console */
+ if (&mdev->mfbdev->mfb == mga_fb)
+ drm_gem_vram_kunmap(gbo);
+ drm_gem_vram_unpin(gbo);
}
crtc->primary->fb = NULL;
}
diff --git a/drivers/gpu/drm/mgag200/mgag200_ttm.c b/drivers/gpu/drm/mgag200/mgag200_ttm.c
index bd42365a8aa8..59294c0fd24a 100644
--- a/drivers/gpu/drm/mgag200/mgag200_ttm.c
+++ b/drivers/gpu/drm/mgag200/mgag200_ttm.c
@@ -26,167 +26,21 @@
* Authors: Dave Airlie <airlied@redhat.com>
*/
#include <drm/drmP.h>
-#include <drm/ttm/ttm_page_alloc.h>
#include "mgag200_drv.h"
-static inline struct mga_device *
-mgag200_bdev(struct ttm_bo_device *bd)
-{
- return container_of(bd, struct mga_device, ttm.bdev);
-}
-
-static void mgag200_bo_ttm_destroy(struct ttm_buffer_object *tbo)
-{
- struct mgag200_bo *bo;
-
- bo = container_of(tbo, struct mgag200_bo, bo);
-
- drm_gem_object_release(&bo->gem);
- kfree(bo);
-}
-
-static bool mgag200_ttm_bo_is_mgag200_bo(struct ttm_buffer_object *bo)
-{
- if (bo->destroy == &mgag200_bo_ttm_destroy)
- return true;
- return false;
-}
-
-static int
-mgag200_bo_init_mem_type(struct ttm_bo_device *bdev, uint32_t type,
- struct ttm_mem_type_manager *man)
-{
- switch (type) {
- case TTM_PL_SYSTEM:
- man->flags = TTM_MEMTYPE_FLAG_MAPPABLE;
- man->available_caching = TTM_PL_MASK_CACHING;
- man->default_caching = TTM_PL_FLAG_CACHED;
- break;
- case TTM_PL_VRAM:
- man->func = &ttm_bo_manager_func;
- man->flags = TTM_MEMTYPE_FLAG_FIXED |
- TTM_MEMTYPE_FLAG_MAPPABLE;
- man->available_caching = TTM_PL_FLAG_UNCACHED |
- TTM_PL_FLAG_WC;
- man->default_caching = TTM_PL_FLAG_WC;
- break;
- default:
- DRM_ERROR("Unsupported memory type %u\n", (unsigned)type);
- return -EINVAL;
- }
- return 0;
-}
-
-static void
-mgag200_bo_evict_flags(struct ttm_buffer_object *bo, struct ttm_placement *pl)
-{
- struct mgag200_bo *mgabo = mgag200_bo(bo);
-
- if (!mgag200_ttm_bo_is_mgag200_bo(bo))
- return;
-
- mgag200_ttm_placement(mgabo, TTM_PL_FLAG_SYSTEM);
- *pl = mgabo->placement;
-}
-
-static int mgag200_bo_verify_access(struct ttm_buffer_object *bo, struct file *filp)
-{
- struct mgag200_bo *mgabo = mgag200_bo(bo);
-
- return drm_vma_node_verify_access(&mgabo->gem.vma_node,
- filp->private_data);
-}
-
-static int mgag200_ttm_io_mem_reserve(struct ttm_bo_device *bdev,
- struct ttm_mem_reg *mem)
-{
- struct ttm_mem_type_manager *man = &bdev->man[mem->mem_type];
- struct mga_device *mdev = mgag200_bdev(bdev);
-
- mem->bus.addr = NULL;
- mem->bus.offset = 0;
- mem->bus.size = mem->num_pages << PAGE_SHIFT;
- mem->bus.base = 0;
- mem->bus.is_iomem = false;
- if (!(man->flags & TTM_MEMTYPE_FLAG_MAPPABLE))
- return -EINVAL;
- switch (mem->mem_type) {
- case TTM_PL_SYSTEM:
- /* system memory */
- return 0;
- case TTM_PL_VRAM:
- mem->bus.offset = mem->start << PAGE_SHIFT;
- mem->bus.base = pci_resource_start(mdev->dev->pdev, 0);
- mem->bus.is_iomem = true;
- break;
- default:
- return -EINVAL;
- break;
- }
- return 0;
-}
-
-static void mgag200_ttm_io_mem_free(struct ttm_bo_device *bdev, struct ttm_mem_reg *mem)
-{
-}
-
-static void mgag200_ttm_backend_destroy(struct ttm_tt *tt)
-{
- ttm_tt_fini(tt);
- kfree(tt);
-}
-
-static struct ttm_backend_func mgag200_tt_backend_func = {
- .destroy = &mgag200_ttm_backend_destroy,
-};
-
-
-static struct ttm_tt *mgag200_ttm_tt_create(struct ttm_buffer_object *bo,
- uint32_t page_flags)
-{
- struct ttm_tt *tt;
-
- tt = kzalloc(sizeof(struct ttm_tt), GFP_KERNEL);
- if (tt == NULL)
- return NULL;
- tt->func = &mgag200_tt_backend_func;
- if (ttm_tt_init(tt, bo, page_flags)) {
- kfree(tt);
- return NULL;
- }
- return tt;
-}
-
-struct ttm_bo_driver mgag200_bo_driver = {
- .ttm_tt_create = mgag200_ttm_tt_create,
- .init_mem_type = mgag200_bo_init_mem_type,
- .eviction_valuable = ttm_bo_eviction_valuable,
- .evict_flags = mgag200_bo_evict_flags,
- .move = NULL,
- .verify_access = mgag200_bo_verify_access,
- .io_mem_reserve = &mgag200_ttm_io_mem_reserve,
- .io_mem_free = &mgag200_ttm_io_mem_free,
-};
-
int mgag200_mm_init(struct mga_device *mdev)
{
+ struct drm_vram_mm *vmm;
int ret;
struct drm_device *dev = mdev->dev;
- struct ttm_bo_device *bdev = &mdev->ttm.bdev;
-
- ret = ttm_bo_device_init(&mdev->ttm.bdev,
- &mgag200_bo_driver,
- dev->anon_inode->i_mapping,
- true);
- if (ret) {
- DRM_ERROR("Error initialising bo driver; %d\n", ret);
- return ret;
- }
- ret = ttm_bo_init_mm(bdev, TTM_PL_VRAM, mdev->mc.vram_size >> PAGE_SHIFT);
- if (ret) {
- DRM_ERROR("Failed ttm VRAM init: %d\n", ret);
+ vmm = drm_vram_helper_alloc_mm(dev, pci_resource_start(dev->pdev, 0),
+ mdev->mc.vram_size,
+ &drm_gem_vram_mm_funcs);
+ if (IS_ERR(vmm)) {
+ ret = PTR_ERR(vmm);
+ DRM_ERROR("Error initializing VRAM MM; %d\n", ret);
return ret;
}
@@ -203,149 +57,10 @@ void mgag200_mm_fini(struct mga_device *mdev)
{
struct drm_device *dev = mdev->dev;
- ttm_bo_device_release(&mdev->ttm.bdev);
+ drm_vram_helper_release_mm(dev);
arch_io_free_memtype_wc(pci_resource_start(dev->pdev, 0),
pci_resource_len(dev->pdev, 0));
arch_phys_wc_del(mdev->fb_mtrr);
mdev->fb_mtrr = 0;
}
-
-void mgag200_ttm_placement(struct mgag200_bo *bo, int domain)
-{
- u32 c = 0;
- unsigned i;
-
- bo->placement.placement = bo->placements;
- bo->placement.busy_placement = bo->placements;
- if (domain & TTM_PL_FLAG_VRAM)
- bo->placements[c++].flags = TTM_PL_FLAG_WC | TTM_PL_FLAG_UNCACHED | TTM_PL_FLAG_VRAM;
- if (domain & TTM_PL_FLAG_SYSTEM)
- bo->placements[c++].flags = TTM_PL_MASK_CACHING | TTM_PL_FLAG_SYSTEM;
- if (!c)
- bo->placements[c++].flags = TTM_PL_MASK_CACHING | TTM_PL_FLAG_SYSTEM;
- bo->placement.num_placement = c;
- bo->placement.num_busy_placement = c;
- for (i = 0; i < c; ++i) {
- bo->placements[i].fpfn = 0;
- bo->placements[i].lpfn = 0;
- }
-}
-
-int mgag200_bo_create(struct drm_device *dev, int size, int align,
- uint32_t flags, struct mgag200_bo **pmgabo)
-{
- struct mga_device *mdev = dev->dev_private;
- struct mgag200_bo *mgabo;
- size_t acc_size;
- int ret;
-
- mgabo = kzalloc(sizeof(struct mgag200_bo), GFP_KERNEL);
- if (!mgabo)
- return -ENOMEM;
-
- ret = drm_gem_object_init(dev, &mgabo->gem, size);
- if (ret) {
- kfree(mgabo);
- return ret;
- }
-
- mgabo->bo.bdev = &mdev->ttm.bdev;
-
- mgag200_ttm_placement(mgabo, TTM_PL_FLAG_VRAM | TTM_PL_FLAG_SYSTEM);
-
- acc_size = ttm_bo_dma_acc_size(&mdev->ttm.bdev, size,
- sizeof(struct mgag200_bo));
-
- ret = ttm_bo_init(&mdev->ttm.bdev, &mgabo->bo, size,
- ttm_bo_type_device, &mgabo->placement,
- align >> PAGE_SHIFT, false, acc_size,
- NULL, NULL, mgag200_bo_ttm_destroy);
- if (ret)
- return ret;
-
- *pmgabo = mgabo;
- return 0;
-}
-
-static inline u64 mgag200_bo_gpu_offset(struct mgag200_bo *bo)
-{
- return bo->bo.offset;
-}
-
-int mgag200_bo_pin(struct mgag200_bo *bo, u32 pl_flag, u64 *gpu_addr)
-{
- struct ttm_operation_ctx ctx = { false, false };
- int i, ret;
-
- if (bo->pin_count) {
- bo->pin_count++;
- if (gpu_addr)
- *gpu_addr = mgag200_bo_gpu_offset(bo);
- return 0;
- }
-
- mgag200_ttm_placement(bo, pl_flag);
- for (i = 0; i < bo->placement.num_placement; i++)
- bo->placements[i].flags |= TTM_PL_FLAG_NO_EVICT;
- ret = ttm_bo_validate(&bo->bo, &bo->placement, &ctx);
- if (ret)
- return ret;
-
- bo->pin_count = 1;
- if (gpu_addr)
- *gpu_addr = mgag200_bo_gpu_offset(bo);
- return 0;
-}
-
-int mgag200_bo_unpin(struct mgag200_bo *bo)
-{
- struct ttm_operation_ctx ctx = { false, false };
- int i;
- if (!bo->pin_count) {
- DRM_ERROR("unpin bad %p\n", bo);
- return 0;
- }
- bo->pin_count--;
- if (bo->pin_count)
- return 0;
-
- for (i = 0; i < bo->placement.num_placement ; i++)
- bo->placements[i].flags &= ~TTM_PL_FLAG_NO_EVICT;
- return ttm_bo_validate(&bo->bo, &bo->placement, &ctx);
-}
-
-int mgag200_bo_push_sysram(struct mgag200_bo *bo)
-{
- struct ttm_operation_ctx ctx = { false, false };
- int i, ret;
- if (!bo->pin_count) {
- DRM_ERROR("unpin bad %p\n", bo);
- return 0;
- }
- bo->pin_count--;
- if (bo->pin_count)
- return 0;
-
- if (bo->kmap.virtual)
- ttm_bo_kunmap(&bo->kmap);
-
- mgag200_ttm_placement(bo, TTM_PL_FLAG_SYSTEM);
- for (i = 0; i < bo->placement.num_placement ; i++)
- bo->placements[i].flags |= TTM_PL_FLAG_NO_EVICT;
-
- ret = ttm_bo_validate(&bo->bo, &bo->placement, &ctx);
- if (ret) {
- DRM_ERROR("pushing to VRAM failed\n");
- return ret;
- }
- return 0;
-}
-
-int mgag200_mmap(struct file *filp, struct vm_area_struct *vma)
-{
- struct drm_file *file_priv = filp->private_data;
- struct mga_device *mdev = file_priv->minor->dev->dev_private;
-
- return ttm_bo_mmap(filp, vma, &mdev->ttm.bdev);
-}