From owner-svn-src-stable-10@FreeBSD.ORG Tue Dec 2 14:09:57 2014 Return-Path: Delivered-To: svn-src-stable-10@freebsd.org Received: from mx1.freebsd.org (mx1.freebsd.org [IPv6:2001:1900:2254:206a::19:1]) (using TLSv1.2 with cipher AECDH-AES256-SHA (256/256 bits)) (No client certificate requested) by hub.freebsd.org (Postfix) with ESMTPS id 1C8CBACA; Tue, 2 Dec 2014 14:09:57 +0000 (UTC) Received: from svn.freebsd.org (svn.freebsd.org [IPv6:2001:1900:2254:2068::e6a:0]) (using TLSv1.2 with cipher ECDHE-RSA-AES256-GCM-SHA384 (256/256 bits)) (Client did not present a certificate) by mx1.freebsd.org (Postfix) with ESMTPS id 074B5D8E; Tue, 2 Dec 2014 14:09:57 +0000 (UTC) Received: from svn.freebsd.org ([127.0.1.70]) by svn.freebsd.org (8.14.9/8.14.9) with ESMTP id sB2E9ump042779; Tue, 2 Dec 2014 14:09:56 GMT (envelope-from tijl@FreeBSD.org) Received: (from tijl@localhost) by svn.freebsd.org (8.14.9/8.14.9/Submit) id sB2E9sZu042768; Tue, 2 Dec 2014 14:09:54 GMT (envelope-from tijl@FreeBSD.org) Message-Id: <201412021409.sB2E9sZu042768@svn.freebsd.org> X-Authentication-Warning: svn.freebsd.org: tijl set sender to tijl@FreeBSD.org using -f From: Tijl Coosemans Date: Tue, 2 Dec 2014 14:09:54 +0000 (UTC) To: src-committers@freebsd.org, svn-src-all@freebsd.org, svn-src-stable@freebsd.org, svn-src-stable-10@freebsd.org Subject: svn commit: r275408 - in stable/10/sys: dev/drm2 dev/drm2/radeon dev/drm2/ttm modules/drm2/drm2 X-SVN-Group: stable-10 MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit X-BeenThere: svn-src-stable-10@freebsd.org X-Mailman-Version: 2.1.18-1 Precedence: list List-Id: SVN commit messages for only the 10-stable src tree List-Unsubscribe: , List-Archive: List-Post: List-Help: List-Subscribe: , X-List-Received-Date: Tue, 02 Dec 2014 14:09:57 -0000 Author: tijl Date: Tue Dec 2 14:09:54 2014 New Revision: 275408 URL: https://svnweb.freebsd.org/changeset/base/275408 Log: MFC r273862,273902: Port the TTM AGP backend to the FreeBSD agp driver and enable AGP support in the radeonkms driver. Note: In PCI mode virtual addresses on the graphics card that map to system RAM are translated to physical addresses by the graphics card itself. In AGP mode address translation is done by the AGP chipset so fictitious addresses appear on the system bus. For the CPU cache management to work correctly when the CPU accesses this memory it needs to use the same fictitious addresses (and let the chipset translate them) instead of using the physical addresses directly. Reviewed by: kib Modified: stable/10/sys/dev/drm2/drm_agpsupport.c stable/10/sys/dev/drm2/radeon/radeon.h stable/10/sys/dev/drm2/radeon/radeon_device.c stable/10/sys/dev/drm2/radeon/radeon_ttm.c stable/10/sys/dev/drm2/ttm/ttm_agp_backend.c stable/10/sys/dev/drm2/ttm/ttm_bo_driver.h stable/10/sys/dev/drm2/ttm/ttm_page_alloc.c stable/10/sys/modules/drm2/drm2/Makefile Directory Properties: stable/10/ (props changed) Modified: stable/10/sys/dev/drm2/drm_agpsupport.c ============================================================================== --- stable/10/sys/dev/drm2/drm_agpsupport.c Tue Dec 2 13:58:57 2014 (r275407) +++ stable/10/sys/dev/drm2/drm_agpsupport.c Tue Dec 2 14:09:54 2014 (r275408) @@ -396,7 +396,7 @@ void *drm_agp_allocate_memory(size_t pag if (!agpdev) return NULL; - return agp_alloc_memory(agpdev, type, pages << AGP_PAGE_SHIFT); + return agp_alloc_memory(agpdev, type, pages << PAGE_SHIFT); } int drm_agp_free_memory(void *handle) Modified: stable/10/sys/dev/drm2/radeon/radeon.h ============================================================================== --- stable/10/sys/dev/drm2/radeon/radeon.h Tue Dec 2 13:58:57 2014 (r275407) +++ stable/10/sys/dev/drm2/radeon/radeon.h Tue Dec 2 14:09:54 2014 (r275408) @@ -1618,6 +1618,7 @@ struct radeon_device { bool need_dma32; bool accel_working; bool fictitious_range_registered; + bool fictitious_agp_range_registered; struct radeon_surface_reg surface_regs[RADEON_GEM_MAX_SURFACES]; const struct firmware *me_fw; /* all family ME firmware */ const struct firmware *pfp_fw; /* r6/700 PFP firmware */ Modified: stable/10/sys/dev/drm2/radeon/radeon_device.c ============================================================================== --- stable/10/sys/dev/drm2/radeon/radeon_device.c Tue Dec 2 13:58:57 2014 (r275407) +++ stable/10/sys/dev/drm2/radeon/radeon_device.c Tue Dec 2 14:09:54 2014 (r275408) @@ -1014,6 +1014,7 @@ int radeon_device_init(struct radeon_dev rdev->mc.gtt_size = radeon_gart_size * 1024 * 1024; rdev->accel_working = false; rdev->fictitious_range_registered = false; + rdev->fictitious_agp_range_registered = false; /* set up ring ids */ for (i = 0; i < RADEON_NUM_RINGS; i++) { rdev->ring[i].idx = i; @@ -1168,6 +1169,24 @@ int radeon_device_init(struct radeon_dev return (-r); } rdev->fictitious_range_registered = true; +#if __OS_HAS_AGP + if (rdev->flags & RADEON_IS_AGP) { + DRM_INFO("%s: Taking over the fictitious range 0x%jx-0x%jx\n", + __func__, (uintmax_t)rdev->mc.agp_base, + (uintmax_t)rdev->mc.agp_base + rdev->mc.gtt_size); + r = vm_phys_fictitious_reg_range( + rdev->mc.agp_base, + rdev->mc.agp_base + rdev->mc.gtt_size, + VM_MEMATTR_WRITE_COMBINING); + if (r != 0) { + DRM_ERROR("Failed to register fictitious range " + "0x%jx-0x%jx (%d).\n", (uintmax_t)rdev->mc.agp_base, + (uintmax_t)rdev->mc.agp_base + rdev->mc.gtt_size, r); + return (-r); + } + rdev->fictitious_agp_range_registered = true; + } +#endif if ((radeon_testing & 1)) { radeon_test_moves(rdev); @@ -1205,6 +1224,13 @@ void radeon_device_fini(struct radeon_de rdev->mc.aper_base, rdev->mc.aper_base + rdev->mc.visible_vram_size); } +#if __OS_HAS_AGP + if (rdev->fictitious_agp_range_registered) { + vm_phys_fictitious_unreg_range( + rdev->mc.agp_base, + rdev->mc.agp_base + rdev->mc.gtt_size); + } +#endif radeon_fini(rdev); #ifdef DUMBBELL_WIP Modified: stable/10/sys/dev/drm2/radeon/radeon_ttm.c ============================================================================== --- stable/10/sys/dev/drm2/radeon/radeon_ttm.c Tue Dec 2 13:58:57 2014 (r275407) +++ stable/10/sys/dev/drm2/radeon/radeon_ttm.c Tue Dec 2 14:09:54 2014 (r275408) @@ -560,12 +560,10 @@ static struct ttm_tt *radeon_ttm_tt_crea rdev = radeon_get_rdev(bdev); #if __OS_HAS_AGP -#ifdef DUMBBELL_WIP if (rdev->flags & RADEON_IS_AGP) { return ttm_agp_tt_create(bdev, rdev->ddev->agp->agpdev, size, page_flags, dummy_read_page); } -#endif /* DUMBBELL_WIP */ #endif gtt = malloc(sizeof(struct radeon_ttm_tt), @@ -610,11 +608,9 @@ static int radeon_ttm_tt_populate(struct rdev = radeon_get_rdev(ttm->bdev); #if __OS_HAS_AGP -#ifdef DUMBBELL_WIP if (rdev->flags & RADEON_IS_AGP) { return ttm_agp_tt_populate(ttm); } -#endif /* DUMBBELL_WIP */ #endif #ifdef CONFIG_SWIOTLB @@ -660,12 +656,10 @@ static void radeon_ttm_tt_unpopulate(str rdev = radeon_get_rdev(ttm->bdev); #if __OS_HAS_AGP -#ifdef DUMBBELL_WIP if (rdev->flags & RADEON_IS_AGP) { ttm_agp_tt_unpopulate(ttm); return; } -#endif /* DUMBBELL_WIP */ #endif #ifdef CONFIG_SWIOTLB Modified: stable/10/sys/dev/drm2/ttm/ttm_agp_backend.c ============================================================================== --- stable/10/sys/dev/drm2/ttm/ttm_agp_backend.c Tue Dec 2 13:58:57 2014 (r275407) +++ stable/10/sys/dev/drm2/ttm/ttm_agp_backend.c Tue Dec 2 14:09:54 2014 (r275408) @@ -41,7 +41,8 @@ __FBSDID("$FreeBSD$"); struct ttm_agp_backend { struct ttm_tt ttm; - struct agp_memory *mem; + vm_offset_t offset; + vm_page_t *pages; device_t bridge; }; @@ -51,31 +52,23 @@ static int ttm_agp_bind(struct ttm_tt *t { struct ttm_agp_backend *agp_be = container_of(ttm, struct ttm_agp_backend, ttm); struct drm_mm_node *node = bo_mem->mm_node; - struct agp_memory *mem; - int ret, cached = (bo_mem->placement & TTM_PL_FLAG_CACHED); + int ret; unsigned i; - mem = agp_alloc_memory(agp_be->bridge, AGP_USER_MEMORY, ttm->num_pages); - if (unlikely(mem == NULL)) - return -ENOMEM; - - mem->page_count = 0; for (i = 0; i < ttm->num_pages; i++) { vm_page_t page = ttm->pages[i]; if (!page) page = ttm->dummy_read_page; - mem->pages[mem->page_count++] = page; + agp_be->pages[i] = page; } - agp_be->mem = mem; - - mem->is_flushed = 1; - mem->type = (cached) ? AGP_USER_CACHED_MEMORY : AGP_USER_MEMORY; - ret = agp_bind_memory(mem, node->start); + agp_be->offset = node->start * PAGE_SIZE; + ret = -agp_bind_pages(agp_be->bridge, agp_be->pages, + ttm->num_pages << PAGE_SHIFT, agp_be->offset); if (ret) - pr_err("AGP Bind memory failed\n"); + printf("[TTM] AGP Bind memory failed\n"); return ret; } @@ -84,22 +77,16 @@ static int ttm_agp_unbind(struct ttm_tt { struct ttm_agp_backend *agp_be = container_of(ttm, struct ttm_agp_backend, ttm); - if (agp_be->mem) { - if (agp_be->mem->is_bound) - return agp_unbind_memory(agp_be->mem); - agp_free_memory(agp_be->mem); - agp_be->mem = NULL; - } - return 0; + return -agp_unbind_pages(agp_be->bridge, ttm->num_pages << PAGE_SHIFT, + agp_be->offset); } static void ttm_agp_destroy(struct ttm_tt *ttm) { struct ttm_agp_backend *agp_be = container_of(ttm, struct ttm_agp_backend, ttm); - if (agp_be->mem) - ttm_agp_unbind(ttm); ttm_tt_fini(ttm); + free(agp_be->pages, M_TTM_AGP); free(agp_be, M_TTM_AGP); } @@ -118,14 +105,18 @@ struct ttm_tt *ttm_agp_tt_create(struct agp_be = malloc(sizeof(*agp_be), M_TTM_AGP, M_WAITOK | M_ZERO); - agp_be->mem = NULL; agp_be->bridge = bridge; agp_be->ttm.func = &ttm_agp_func; if (ttm_tt_init(&agp_be->ttm, bdev, size, page_flags, dummy_read_page)) { + free(agp_be, M_TTM_AGP); return NULL; } + agp_be->offset = 0; + agp_be->pages = malloc(agp_be->ttm.num_pages * sizeof(*agp_be->pages), + M_TTM_AGP, M_WAITOK); + return &agp_be->ttm; } Modified: stable/10/sys/dev/drm2/ttm/ttm_bo_driver.h ============================================================================== --- stable/10/sys/dev/drm2/ttm/ttm_bo_driver.h Tue Dec 2 13:58:57 2014 (r275407) +++ stable/10/sys/dev/drm2/ttm/ttm_bo_driver.h Tue Dec 2 14:09:54 2014 (r275408) @@ -990,9 +990,8 @@ extern vm_memattr_t ttm_io_prot(uint32_t extern const struct ttm_mem_type_manager_func ttm_bo_manager_func; -#if (defined(CONFIG_AGP) || (defined(CONFIG_AGP_MODULE) && defined(MODULE))) +#if __OS_HAS_AGP #define TTM_HAS_AGP -#include /** * ttm_agp_tt_create @@ -1009,7 +1008,7 @@ extern const struct ttm_mem_type_manager * bind and unbind memory backing a ttm_tt. */ extern struct ttm_tt *ttm_agp_tt_create(struct ttm_bo_device *bdev, - struct agp_bridge_data *bridge, + device_t bridge, unsigned long size, uint32_t page_flags, struct vm_page *dummy_read_page); int ttm_agp_tt_populate(struct ttm_tt *ttm); Modified: stable/10/sys/dev/drm2/ttm/ttm_page_alloc.c ============================================================================== --- stable/10/sys/dev/drm2/ttm/ttm_page_alloc.c Tue Dec 2 13:58:57 2014 (r275407) +++ stable/10/sys/dev/drm2/ttm/ttm_page_alloc.c Tue Dec 2 14:09:54 2014 (r275408) @@ -45,10 +45,6 @@ __FBSDID("$FreeBSD$"); #include #include -#ifdef TTM_HAS_AGP -#include -#endif - #define NUM_PAGES_TO_ALLOC (PAGE_SIZE/sizeof(vm_page_t)) #define SMALL_ALLOCATION 16 #define FREE_ALL_PAGES (~0U) @@ -220,46 +216,34 @@ static struct ttm_pool_manager *_manager static int set_pages_array_wb(vm_page_t *pages, int addrinarray) { - vm_page_t m; +#ifdef TTM_HAS_AGP int i; - for (i = 0; i < addrinarray; i++) { - m = pages[i]; -#ifdef TTM_HAS_AGP - unmap_page_from_agp(m); + for (i = 0; i < addrinarray; i++) + pmap_page_set_memattr(pages[i], VM_MEMATTR_WRITE_BACK); #endif - pmap_page_set_memattr(m, VM_MEMATTR_WRITE_BACK); - } return 0; } static int set_pages_array_wc(vm_page_t *pages, int addrinarray) { - vm_page_t m; +#ifdef TTM_HAS_AGP int i; - for (i = 0; i < addrinarray; i++) { - m = pages[i]; -#ifdef TTM_HAS_AGP - map_page_into_agp(pages[i]); + for (i = 0; i < addrinarray; i++) + pmap_page_set_memattr(pages[i], VM_MEMATTR_WRITE_COMBINING); #endif - pmap_page_set_memattr(m, VM_MEMATTR_WRITE_COMBINING); - } return 0; } static int set_pages_array_uc(vm_page_t *pages, int addrinarray) { - vm_page_t m; +#ifdef TTM_HAS_AGP int i; - for (i = 0; i < addrinarray; i++) { - m = pages[i]; -#ifdef TTM_HAS_AGP - map_page_into_agp(pages[i]); + for (i = 0; i < addrinarray; i++) + pmap_page_set_memattr(pages[i], VM_MEMATTR_UNCACHEABLE); #endif - pmap_page_set_memattr(m, VM_MEMATTR_UNCACHEABLE); - } return 0; } Modified: stable/10/sys/modules/drm2/drm2/Makefile ============================================================================== --- stable/10/sys/modules/drm2/drm2/Makefile Tue Dec 2 13:58:57 2014 (r275407) +++ stable/10/sys/modules/drm2/drm2/Makefile Tue Dec 2 14:09:54 2014 (r275408) @@ -35,6 +35,7 @@ SRCS = \ drm_stub.c \ drm_sysctl.c \ drm_vm.c \ + ttm_agp_backend.c \ ttm_lock.c \ ttm_object.c \ ttm_tt.c \ @@ -46,7 +47,6 @@ SRCS = \ ttm_page_alloc.c \ ttm_bo_vm.c \ ati_pcigart.c -#ttm_agp_backend.c #ttm_page_alloc_dma.c .if ${MACHINE_CPUARCH} == "amd64"