From 1403b1a38e8b19a4cc17e2c158e278628943a436 Mon Sep 17 00:00:00 2001 From: Pauli Nieminen Date: Thu, 1 Apr 2010 12:44:57 +0000 Subject: drm/ttm: add pool wc/uc page allocator V3 On AGP system we might allocate/free routinely uncached or wc memory, changing page from cached (wb) to uc or wc is very expensive and involves a lot of flushing. To improve performance this allocator use a pool of uc,wc pages. Pools are protected with spinlocks to allow multiple threads to allocate pages simultanously. Expensive operations are done outside of spinlock to maximize concurrency. Pools are linked lists of pages that were recently freed. mm shrink callback allows kernel to claim back pages when they are required for something else. Fixes: * set_pages_array_wb handles highmem pages so we don't have to remove them from pool. * Add count parameter to ttm_put_pages to avoid looping in free code. * Change looping from _safe to normal in pool fill error path. * Initialize sum variable and make the loop prettier in get_num_unused_pages. * Moved pages_freed reseting inside the loop in ttm_page_pool_free. * Add warning comment about spinlock context in ttm_page_pool_free. Based on Jerome Glisse's and Dave Airlie's pool allocator. Signed-off-by: Jerome Glisse Signed-off-by: Dave Airlie Signed-off-by: Pauli Nieminen Reviewed-by: Jerome Glisse Signed-off-by: Dave Airlie --- include/drm/ttm/ttm_page_alloc.h | 70 ++++++++++++++++++++++++++++++++++++++++ 1 file changed, 70 insertions(+) create mode 100644 include/drm/ttm/ttm_page_alloc.h (limited to 'include/drm') diff --git a/include/drm/ttm/ttm_page_alloc.h b/include/drm/ttm/ttm_page_alloc.h new file mode 100644 index 000000000000..043d817b8164 --- /dev/null +++ b/include/drm/ttm/ttm_page_alloc.h @@ -0,0 +1,70 @@ +/* + * Copyright (c) Red Hat Inc. + + * Permission is hereby granted, free of charge, to any person obtaining a + * copy of this software and associated documentation files (the "Software"), + * to deal in the Software without restriction, including without limitation + * the rights to use, copy, modify, merge, publish, distribute, sub license, + * and/or sell copies of the Software, and to permit persons to whom the + * Software is furnished to do so, subject to the following conditions: + * + * The above copyright notice and this permission notice (including the + * next paragraph) shall be included in all copies or substantial portions + * of the Software. + * + * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR + * IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, + * FITNESS FOR A PARTICULAR PURPOSE AND NON-INFRINGEMENT. IN NO EVENT SHALL + * THE AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER + * LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING + * FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER + * DEALINGS IN THE SOFTWARE. + * + * Authors: Dave Airlie + * Jerome Glisse + */ +#ifndef TTM_PAGE_ALLOC +#define TTM_PAGE_ALLOC + +#include "ttm_bo_driver.h" +#include "ttm_memory.h" + +/** + * Get count number of pages from pool to pages list. + * + * @pages: heado of empty linked list where pages are filled. + * @flags: ttm flags for page allocation. + * @cstate: ttm caching state for the page. + * @count: number of pages to allocate. + */ +int ttm_get_pages(struct list_head *pages, + int flags, + enum ttm_caching_state cstate, + unsigned count); +/** + * Put linked list of pages to pool. + * + * @pages: list of pages to free. + * @page_count: number of pages in the list. Zero can be passed for unknown + * count. + * @flags: ttm flags for page allocation. + * @cstate: ttm caching state. + */ +void ttm_put_pages(struct list_head *pages, + unsigned page_count, + int flags, + enum ttm_caching_state cstate); +/** + * Initialize pool allocator. + * + * Pool allocator is internaly reference counted so it can be initialized + * multiple times but ttm_page_alloc_fini has to be called same number of + * times. + */ +int ttm_page_alloc_init(unsigned max_pages); +/** + * Free pool allocator. + */ +void ttm_page_alloc_fini(void); + +#endif -- cgit v1.2.3 From 0745866165598b067442c472911280527b08be3e Mon Sep 17 00:00:00 2001 From: Pauli Nieminen Date: Thu, 1 Apr 2010 12:44:58 +0000 Subject: drm/ttm: Add debugfs output entry to pool allocator. ttm_page_alloc_debugfs can be registered to output the state of pools. Debugfs file will output number of pages freed from the pool, number of pages in pool now and the lowes number of pages in pool since previous shrink. Signed-off-by: Pauli Nieminen Signed-off-by: Dave Airlie --- include/drm/ttm/ttm_page_alloc.h | 4 ++++ 1 file changed, 4 insertions(+) (limited to 'include/drm') diff --git a/include/drm/ttm/ttm_page_alloc.h b/include/drm/ttm/ttm_page_alloc.h index 043d817b8164..8b091c309df4 100644 --- a/include/drm/ttm/ttm_page_alloc.h +++ b/include/drm/ttm/ttm_page_alloc.h @@ -67,4 +67,8 @@ int ttm_page_alloc_init(unsigned max_pages); */ void ttm_page_alloc_fini(void); +/** + * Output the state of pools to debugfs file + */ +extern int ttm_page_alloc_debugfs(struct seq_file *m, void *data); #endif -- cgit v1.2.3 From c96af79e3463d5d3f865625baa8bb8aa4c0944a0 Mon Sep 17 00:00:00 2001 From: Pauli Nieminen Date: Thu, 1 Apr 2010 12:45:03 +0000 Subject: drm/ttm: Add sysfs interface to control pool allocator. Sysfs interface allows user to configure pool allocator functionality and change limits for the size of pool. Signed-off-by: Pauli Nieminen Signed-off-by: Dave Airlie --- include/drm/ttm/ttm_page_alloc.h | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) (limited to 'include/drm') diff --git a/include/drm/ttm/ttm_page_alloc.h b/include/drm/ttm/ttm_page_alloc.h index 8b091c309df4..8bb4de567b2c 100644 --- a/include/drm/ttm/ttm_page_alloc.h +++ b/include/drm/ttm/ttm_page_alloc.h @@ -61,7 +61,7 @@ void ttm_put_pages(struct list_head *pages, * multiple times but ttm_page_alloc_fini has to be called same number of * times. */ -int ttm_page_alloc_init(unsigned max_pages); +int ttm_page_alloc_init(struct ttm_mem_global *glob, unsigned max_pages); /** * Free pool allocator. */ -- cgit v1.2.3