]> asedeno.scripts.mit.edu Git - linux.git/commitdiff
drm, agpgart: Use pgprot_writecombine for AGP maps and make the MTRR optional
authorAndy Lutomirski <luto@amacapital.net>
Mon, 13 May 2013 23:58:43 +0000 (23:58 +0000)
committerDave Airlie <airlied@redhat.com>
Fri, 31 May 2013 03:37:31 +0000 (13:37 +1000)
I'm not sure I understand the intent of the previous behavior.  mmap
on /dev/agpgart and DRM_AGP maps had no cache flags set, so they
would be fully cacheable.  But the DRM code (most of the time) would
add a write-combining MTRR that would change the effective memory
type to WC.

The new behavior just requests WC explicitly for all AGP maps.

If there is any code out there that expects cacheable access to the
AGP aperture (because the drm driver doesn't request an MTRR or
because it's using /dev/agpgart directly), then it will now end up
with a UC or WC mapping, depending on the architecture and PAT
availability.  But cacheable access to the aperture seems like it's
asking for trouble, because, AIUI, the aperture is an alias of RAM.

Reviewed-by: Daniel Vetter <daniel.vetter@ffwll.ch>
Signed-off-by: Andy Lutomirski <luto@amacapital.net>
Signed-off-by: Dave Airlie <airlied@redhat.com>
drivers/char/agp/frontend.c
drivers/gpu/drm/drm_pci.c
drivers/gpu/drm/drm_stub.c
drivers/gpu/drm/drm_vm.c

index 2e044338753cb4d14cef934126ec15f472d09bb2..1b192395a90c840d48362fdf81a139a75243e08f 100644 (file)
@@ -603,7 +603,8 @@ static int agp_mmap(struct file *file, struct vm_area_struct *vma)
                        vma->vm_ops = kerninfo.vm_ops;
                } else if (io_remap_pfn_range(vma, vma->vm_start,
                                (kerninfo.aper_base + offset) >> PAGE_SHIFT,
-                                           size, vma->vm_page_prot)) {
+                               size,
+                               pgprot_writecombine(vma->vm_page_prot))) {
                        goto out_again;
                }
                mutex_unlock(&(agp_fe.agp_mutex));
@@ -618,8 +619,9 @@ static int agp_mmap(struct file *file, struct vm_area_struct *vma)
                if (kerninfo.vm_ops) {
                        vma->vm_ops = kerninfo.vm_ops;
                } else if (io_remap_pfn_range(vma, vma->vm_start,
-                                           kerninfo.aper_base >> PAGE_SHIFT,
-                                           size, vma->vm_page_prot)) {
+                               kerninfo.aper_base >> PAGE_SHIFT,
+                               size,
+                               pgprot_writecombine(vma->vm_page_prot))) {
                        goto out_again;
                }
                mutex_unlock(&(agp_fe.agp_mutex));
index 14194b6ef64429b53a59c9bd94145a666fe8ddce..80c0b2b298017a0e1810c7db27cd97ca4bb87d6d 100644 (file)
@@ -278,10 +278,10 @@ static int drm_pci_agp_init(struct drm_device *dev)
                }
                if (drm_core_has_MTRR(dev)) {
                        if (dev->agp)
-                               dev->agp->agp_mtrr =
-                                       mtrr_add(dev->agp->agp_info.aper_base,
-                                                dev->agp->agp_info.aper_size *
-                                                1024 * 1024, MTRR_TYPE_WRCOMB, 1);
+                               dev->agp->agp_mtrr = arch_phys_wc_add(
+                                       dev->agp->agp_info.aper_base,
+                                       dev->agp->agp_info.aper_size *
+                                       1024 * 1024);
                }
        }
        return 0;
index 16f3ec579b3bb2b8448523422634cf3fcdbb70c1..577786ce9fbc40e2fbcd549819023d1fa29ba419 100644 (file)
@@ -451,14 +451,8 @@ void drm_put_dev(struct drm_device *dev)
 
        drm_lastclose(dev);
 
-       if (drm_core_has_MTRR(dev) && drm_core_has_AGP(dev) &&
-           dev->agp && dev->agp->agp_mtrr >= 0) {
-               int retval;
-               retval = mtrr_del(dev->agp->agp_mtrr,
-                                 dev->agp->agp_info.aper_base,
-                                 dev->agp->agp_info.aper_size * 1024 * 1024);
-               DRM_DEBUG("mtrr_del=%d\n", retval);
-       }
+       if (drm_core_has_MTRR(dev) && drm_core_has_AGP(dev) && dev->agp)
+               arch_phys_wc_del(dev->agp->agp_mtrr);
 
        if (dev->driver->unload)
                dev->driver->unload(dev);
index 43e7825d37172f2e04da4565b085826f2041b5ab..1575694ccacacfa041656422f0d26e45f458eefd 100644 (file)
@@ -49,13 +49,10 @@ static pgprot_t drm_io_prot(struct drm_local_map *map,
        pgprot_t tmp = vm_get_page_prot(vma->vm_flags);
 
 #if defined(__i386__) || defined(__x86_64__)
-       if (map->type != _DRM_AGP) {
-               if (map->type == _DRM_FRAME_BUFFER ||
-                   map->flags & _DRM_WRITE_COMBINING)
-                       tmp = pgprot_writecombine(tmp);
-               else
-                       tmp = pgprot_noncached(tmp);
-       }
+       if (map->type == _DRM_REGISTERS && !(map->flags & _DRM_WRITE_COMBINING))
+               tmp = pgprot_noncached(tmp);
+       else
+               tmp = pgprot_writecombine(tmp);
 #elif defined(__powerpc__)
        pgprot_val(tmp) |= _PAGE_NO_CACHE;
        if (map->type == _DRM_REGISTERS)