From 1c787f0d396c309131d5f34939598d657ee2459f Mon Sep 17 00:00:00 2001 From: Thomas Hellstrom Date: Mon, 21 Aug 2006 20:38:57 +0200 Subject: Backwards compatibility code for ttms. --- linux-core/drm_compat.h | 18 ++++++++++++++++++ 1 file changed, 18 insertions(+) (limited to 'linux-core/drm_compat.h') diff --git a/linux-core/drm_compat.h b/linux-core/drm_compat.h index 407853d7..80928319 100644 --- a/linux-core/drm_compat.h +++ b/linux-core/drm_compat.h @@ -227,4 +227,22 @@ static inline int remap_pfn_range(struct vm_area_struct *vma, unsigned long from } #endif +#include +#include + +/* + * Flush relevant caches and clear a VMA structure so that page references + * will cause a page fault. Don't flush tlbs. + */ + +extern void drm_clear_vma(struct vm_area_struct *vma, + unsigned long addr, unsigned long end); + +/* + * Return the PTE protection map entries for the VMA flags given by + * flags. This is a functional interface to the kernel's protection map. + */ + +extern pgprot_t drm_prot_map(uint32_t flags); + #endif -- cgit v1.2.3 From 1d3cf107d20cb11ad07667622785ef8341ab9c2a Mon Sep 17 00:00:00 2001 From: Thomas Hellstrom Date: Fri, 25 Aug 2006 18:14:22 +0200 Subject: Module protection map access is moving into mainline kernels. Update drm_compat accordingly. (Reported by Dave Airlie) --- linux-core/drm_compat.h | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) (limited to 'linux-core/drm_compat.h') diff --git a/linux-core/drm_compat.h b/linux-core/drm_compat.h index 80928319..779a7000 100644 --- a/linux-core/drm_compat.h +++ b/linux-core/drm_compat.h @@ -243,6 +243,6 @@ extern void drm_clear_vma(struct vm_area_struct *vma, * flags. This is a functional interface to the kernel's protection map. */ -extern pgprot_t drm_prot_map(uint32_t flags); +extern pgprot_t vm_get_page_prot(unsigned long vm_flags); #endif -- cgit v1.2.3 From 235f6fc650e9974211843b9196a903963dae0211 Mon Sep 17 00:00:00 2001 From: Thomas Hellstrom Date: Wed, 27 Sep 2006 09:27:31 +0200 Subject: Adapt to architecture-specific hooks for gatt pages. --- linux-core/drm_compat.h | 23 +++++++++++++++++++++++ 1 file changed, 23 insertions(+) (limited to 'linux-core/drm_compat.h') diff --git a/linux-core/drm_compat.h b/linux-core/drm_compat.h index 779a7000..cf84a70b 100644 --- a/linux-core/drm_compat.h +++ b/linux-core/drm_compat.h @@ -31,6 +31,7 @@ * OTHER DEALINGS IN THE SOFTWARE. */ +#include #ifndef _DRM_COMPAT_H_ #define _DRM_COMPAT_H_ @@ -245,4 +246,26 @@ extern void drm_clear_vma(struct vm_area_struct *vma, extern pgprot_t vm_get_page_prot(unsigned long vm_flags); +/* + * These are similar to the current kernel gatt pages allocator, only that we + * want a struct page pointer instead of a virtual address. This allows for pages + * that are not in the kernel linear map. + */ + +#define drm_alloc_gatt_pages(order) virt_to_page(alloc_gatt_pages(order)) +#define drm_free_gatt_pages(pages, order) free_gatt_pages(page_address(pages), order) + +#if defined(CONFIG_X86) && (LINUX_VERSION_CODE < KERNEL_VERSION(2,6,15)) + +/* + * These are too slow in earlier kernels. + */ + +extern int drm_unmap_page_from_agp(struct page *page); +extern int drm_map_page_into_agp(struct page *page); + +#define map_page_into_agp drm_map_page_into_agp +#define unmap_page_from_agp drm_unmap_page_from_agp +#endif + #endif -- cgit v1.2.3 From c58574c60505a699e19e1ed59e1b441be2594e53 Mon Sep 17 00:00:00 2001 From: Thomas Hellstrom Date: Tue, 10 Oct 2006 10:37:26 +0200 Subject: Use a nopage-based approach to fault in pfns. --- linux-core/drm_compat.h | 27 ++++++++++++++++++++++++++- 1 file changed, 26 insertions(+), 1 deletion(-) (limited to 'linux-core/drm_compat.h') diff --git a/linux-core/drm_compat.h b/linux-core/drm_compat.h index cf84a70b..784b9a7d 100644 --- a/linux-core/drm_compat.h +++ b/linux-core/drm_compat.h @@ -252,7 +252,9 @@ extern pgprot_t vm_get_page_prot(unsigned long vm_flags); * that are not in the kernel linear map. */ -#define drm_alloc_gatt_pages(order) virt_to_page(alloc_gatt_pages(order)) +#define drm_alloc_gatt_pages(order) ({ \ + void *_virt = alloc_gatt_pages(order); \ + ((_virt) ? virt_to_page(_virt) : NULL);}) #define drm_free_gatt_pages(pages, order) free_gatt_pages(page_address(pages), order) #if defined(CONFIG_X86) && (LINUX_VERSION_CODE < KERNEL_VERSION(2,6,15)) @@ -268,4 +270,27 @@ extern int drm_map_page_into_agp(struct page *page); #define unmap_page_from_agp drm_unmap_page_from_agp #endif +#if (LINUX_VERSION_CODE < KERNEL_VERSION(2,6,19)) + +/* + * Hopefully, real NOPAGE_RETRY functionality will be in 2.6.19. + * For now, just return a dummy page that we've allocated out of + * static space. The page will be put by do_nopage() since we've already + * filled out the pte. + */ +extern struct page * get_nopage_retry(void); +extern void free_nopage_retry(void); + +#define NOPAGE_RETRY get_nopage_retry() + +#endif + +/* + * Is the PTE for this address really clear so that we can use + * io_remap_pfn_range? + */ + +int drm_pte_is_clear(struct vm_area_struct *vma, + unsigned long addr); + #endif -- cgit v1.2.3 From f2db76e2f206d2017f710eaddc4b33add4498898 Mon Sep 17 00:00:00 2001 From: Thomas Hellstrom Date: Wed, 11 Oct 2006 13:40:35 +0200 Subject: Big update: Adapt for new functions in the 2.6.19 kernel. Remove the ability to have multiple regions in one TTM. This simplifies a lot of code. Remove the ability to access TTMs from user space. We don't need it anymore without ttm regions. Don't change caching policy for evicted buffers. Instead change it only when the buffer is accessed by the CPU (on the first page fault). This tremendously speeds up eviction rates. Current code is safe for kernels <= 2.6.14. Should also be OK with 2.6.19 and above. --- linux-core/drm_compat.h | 29 ++++++++++++++++++++--------- 1 file changed, 20 insertions(+), 9 deletions(-) (limited to 'linux-core/drm_compat.h') diff --git a/linux-core/drm_compat.h b/linux-core/drm_compat.h index 784b9a7d..4e95679d 100644 --- a/linux-core/drm_compat.h +++ b/linux-core/drm_compat.h @@ -278,19 +278,30 @@ extern int drm_map_page_into_agp(struct page *page); * static space. The page will be put by do_nopage() since we've already * filled out the pte. */ -extern struct page * get_nopage_retry(void); + +struct fault_data { + struct vm_area_struct *vma; + unsigned long address; + pgoff_t pgoff; + unsigned int flags; + + int type; +}; + +extern struct page *get_nopage_retry(void); extern void free_nopage_retry(void); -#define NOPAGE_RETRY get_nopage_retry() +#define NOPAGE_REFAULT get_nopage_retry() -#endif +extern int vm_insert_pfn(struct vm_area_struct *vma, unsigned long addr, + unsigned long pfn, pgprot_t pgprot); -/* - * Is the PTE for this address really clear so that we can use - * io_remap_pfn_range? - */ +extern struct page *drm_vm_ttm_nopage(struct vm_area_struct *vma, + unsigned long address, + int *type); -int drm_pte_is_clear(struct vm_area_struct *vma, - unsigned long addr); +extern struct page *drm_vm_ttm_fault(struct vm_area_struct *vma, + struct fault_data *data); #endif +#endif -- cgit v1.2.3 From 30703893674b3da5b862dee2acd6efca13424398 Mon Sep 17 00:00:00 2001 From: Thomas Hellstrom Date: Wed, 11 Oct 2006 22:21:01 +0200 Subject: Compatibility code for 2.6.15-2.6.18. It is ugly but a little comfort is that it will go away in the mainstream kernel. Some bugfixes, mainly in error paths. --- linux-core/drm_compat.h | 68 +++++++++++++++++++++++++++++++++++++++++++++++++ 1 file changed, 68 insertions(+) (limited to 'linux-core/drm_compat.h') diff --git a/linux-core/drm_compat.h b/linux-core/drm_compat.h index 4e95679d..5617fb7f 100644 --- a/linux-core/drm_compat.h +++ b/linux-core/drm_compat.h @@ -231,6 +231,13 @@ static inline int remap_pfn_range(struct vm_area_struct *vma, unsigned long from #include #include +#if ((LINUX_VERSION_CODE < KERNEL_VERSION(2,6,19)) && \ + (LINUX_VERSION_CODE >= KERNEL_VERSION(2,6,15))) +#define DRM_ODD_MM_COMPAT +#endif + + + /* * Flush relevant caches and clear a VMA structure so that page references * will cause a page fault. Don't flush tlbs. @@ -303,5 +310,66 @@ extern struct page *drm_vm_ttm_nopage(struct vm_area_struct *vma, extern struct page *drm_vm_ttm_fault(struct vm_area_struct *vma, struct fault_data *data); +#endif + +#ifdef DRM_ODD_MM_COMPAT + +struct drm_ttm; + + +/* + * Add a vma to the ttm vma list, and the + * process mm pointer to the ttm mm list. Needs the ttm mutex. + */ + +extern int drm_ttm_add_vma(struct drm_ttm * ttm, + struct vm_area_struct *vma); +/* + * Delete a vma and the corresponding mm pointer from the + * ttm lists. Needs the ttm mutex. + */ +extern void drm_ttm_delete_vma(struct drm_ttm * ttm, + struct vm_area_struct *vma); + +/* + * Attempts to lock all relevant mmap_sems for a ttm, while + * not releasing the ttm mutex. May return -EAGAIN to avoid + * deadlocks. In that case the caller shall release the ttm mutex, + * schedule() and try again. + */ + +extern int drm_ttm_lock_mm(struct drm_ttm * ttm); + +/* + * Unlock all relevant mmap_sems for a ttm. + */ +extern void drm_ttm_unlock_mm(struct drm_ttm * ttm); + +/* + * If the ttm was bound to the aperture, this function shall be called + * with all relevant mmap sems held. It deletes the flag VM_PFNMAP from all + * vmas mapping this ttm. This is needed just after unmapping the ptes of + * the vma, otherwise the do_nopage() function will bug :(. The function + * releases the mmap_sems for this ttm. + */ + +extern void drm_ttm_finish_unmap(struct drm_ttm *ttm); + +/* + * Remap all vmas of this ttm using io_remap_pfn_range. We cannot + * fault these pfns in, because the first one will set the vma VM_PFNMAP + * flag, which will make the next fault bug in do_nopage(). The function + * releases the mmap_sems for this ttm. + */ + +extern int drm_ttm_remap_bound(struct drm_ttm *ttm); + + +/* + * Remap a vma for a bound ttm. Call with the ttm mutex held and + * the relevant mmap_sem locked. + */ +extern int drm_ttm_map_bound(struct vm_area_struct *vma); + #endif #endif -- cgit v1.2.3 From 3624e43282b0c6aad32829f116fd8f7bce66fbb6 Mon Sep 17 00:00:00 2001 From: Thomas Hellstrom Date: Fri, 20 Oct 2006 15:06:31 +0200 Subject: Bug #8707, 2.6.19-rc compatibility for memory manager code. --- linux-core/drm_compat.h | 22 +++++++++++++--------- 1 file changed, 13 insertions(+), 9 deletions(-) (limited to 'linux-core/drm_compat.h') diff --git a/linux-core/drm_compat.h b/linux-core/drm_compat.h index 5617fb7f..a1a94399 100644 --- a/linux-core/drm_compat.h +++ b/linux-core/drm_compat.h @@ -231,7 +231,7 @@ static inline int remap_pfn_range(struct vm_area_struct *vma, unsigned long from #include #include -#if ((LINUX_VERSION_CODE < KERNEL_VERSION(2,6,19)) && \ +#if ((LINUX_VERSION_CODE < KERNEL_VERSION(2,6,20)) && \ (LINUX_VERSION_CODE >= KERNEL_VERSION(2,6,15))) #define DRM_ODD_MM_COMPAT #endif @@ -277,7 +277,18 @@ extern int drm_map_page_into_agp(struct page *page); #define unmap_page_from_agp drm_unmap_page_from_agp #endif -#if (LINUX_VERSION_CODE < KERNEL_VERSION(2,6,19)) +#if (LINUX_VERSION_CODE < KERNEL_VERSION(2,6,15)) +extern struct page *get_nopage_retry(void); +extern void free_nopage_retry(void); +struct fault_data; +extern struct page *drm_vm_ttm_fault(struct vm_area_struct *vma, + struct fault_data *data); + +#define NOPAGE_REFAULT get_nopage_retry() +#endif + + +#if (LINUX_VERSION_CODE < KERNEL_VERSION(2,6,20)) /* * Hopefully, real NOPAGE_RETRY functionality will be in 2.6.19. @@ -295,10 +306,6 @@ struct fault_data { int type; }; -extern struct page *get_nopage_retry(void); -extern void free_nopage_retry(void); - -#define NOPAGE_REFAULT get_nopage_retry() extern int vm_insert_pfn(struct vm_area_struct *vma, unsigned long addr, unsigned long pfn, pgprot_t pgprot); @@ -307,9 +314,6 @@ extern struct page *drm_vm_ttm_nopage(struct vm_area_struct *vma, unsigned long address, int *type); -extern struct page *drm_vm_ttm_fault(struct vm_area_struct *vma, - struct fault_data *data); - #endif #ifdef DRM_ODD_MM_COMPAT -- cgit v1.2.3