Path: blob/master/drivers/gpu/drm/amd/amdgpu/amdgpu_benchmark.c
26517 views
/*1* Copyright 2009 Jerome Glisse.2*3* Permission is hereby granted, free of charge, to any person obtaining a4* copy of this software and associated documentation files (the "Software"),5* to deal in the Software without restriction, including without limitation6* the rights to use, copy, modify, merge, publish, distribute, sublicense,7* and/or sell copies of the Software, and to permit persons to whom the8* Software is furnished to do so, subject to the following conditions:9*10* The above copyright notice and this permission notice shall be included in11* all copies or substantial portions of the Software.12*13* THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR14* IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,15* FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL16* THE COPYRIGHT HOLDER(S) OR AUTHOR(S) BE LIABLE FOR ANY CLAIM, DAMAGES OR17* OTHER LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE,18* ARISING FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR19* OTHER DEALINGS IN THE SOFTWARE.20*21* Authors: Jerome Glisse22*/2324#include <drm/amdgpu_drm.h>25#include "amdgpu.h"2627#define AMDGPU_BENCHMARK_ITERATIONS 102428#define AMDGPU_BENCHMARK_COMMON_MODES_N 172930static int amdgpu_benchmark_do_move(struct amdgpu_device *adev, unsigned size,31uint64_t saddr, uint64_t daddr, int n, s64 *time_ms)32{33ktime_t stime, etime;34struct dma_fence *fence;35int i, r;3637stime = ktime_get();38for (i = 0; i < n; i++) {39struct amdgpu_ring *ring = adev->mman.buffer_funcs_ring;40r = amdgpu_copy_buffer(ring, saddr, daddr, size, NULL, &fence,41false, false, 0);42if (r)43goto exit_do_move;44r = dma_fence_wait(fence, false);45dma_fence_put(fence);46if (r)47goto exit_do_move;48}4950exit_do_move:51etime = ktime_get();52*time_ms = ktime_ms_delta(etime, stime);5354return r;55}565758static void amdgpu_benchmark_log_results(struct amdgpu_device *adev,59int n, unsigned size,60s64 time_ms,61unsigned sdomain, unsigned ddomain,62char *kind)63{64s64 throughput = (n * (size >> 10));6566throughput = div64_s64(throughput, time_ms);6768dev_info(adev->dev, "amdgpu: %s %u bo moves of %u kB from"69" %d to %d in %lld ms, throughput: %lld Mb/s or %lld MB/s\n",70kind, n, size >> 10, sdomain, ddomain, time_ms,71throughput * 8, throughput);72}7374static int amdgpu_benchmark_move(struct amdgpu_device *adev, unsigned size,75unsigned sdomain, unsigned ddomain)76{77struct amdgpu_bo *dobj = NULL;78struct amdgpu_bo *sobj = NULL;79uint64_t saddr, daddr;80s64 time_ms;81int r, n;8283n = AMDGPU_BENCHMARK_ITERATIONS;8485r = amdgpu_bo_create_kernel(adev, size,86PAGE_SIZE, sdomain,87&sobj,88&saddr,89NULL);90if (r)91goto out_cleanup;92r = amdgpu_bo_create_kernel(adev, size,93PAGE_SIZE, ddomain,94&dobj,95&daddr,96NULL);97if (r)98goto out_cleanup;99100if (adev->mman.buffer_funcs) {101r = amdgpu_benchmark_do_move(adev, size, saddr, daddr, n, &time_ms);102if (r)103goto out_cleanup;104else105amdgpu_benchmark_log_results(adev, n, size, time_ms,106sdomain, ddomain, "dma");107}108109out_cleanup:110/* Check error value now. The value can be overwritten when clean up.*/111if (r < 0)112dev_info(adev->dev, "Error while benchmarking BO move.\n");113114if (sobj)115amdgpu_bo_free_kernel(&sobj, &saddr, NULL);116if (dobj)117amdgpu_bo_free_kernel(&dobj, &daddr, NULL);118return r;119}120121int amdgpu_benchmark(struct amdgpu_device *adev, int test_number)122{123int i, r;124static const int common_modes[AMDGPU_BENCHMARK_COMMON_MODES_N] = {125640 * 480 * 4,126720 * 480 * 4,127800 * 600 * 4,128848 * 480 * 4,1291024 * 768 * 4,1301152 * 768 * 4,1311280 * 720 * 4,1321280 * 800 * 4,1331280 * 854 * 4,1341280 * 960 * 4,1351280 * 1024 * 4,1361440 * 900 * 4,1371400 * 1050 * 4,1381680 * 1050 * 4,1391600 * 1200 * 4,1401920 * 1080 * 4,1411920 * 1200 * 4142};143144mutex_lock(&adev->benchmark_mutex);145switch (test_number) {146case 1:147dev_info(adev->dev,148"benchmark test: %d (simple test, VRAM to GTT and GTT to VRAM)\n",149test_number);150/* simple test, VRAM to GTT and GTT to VRAM */151r = amdgpu_benchmark_move(adev, 1024*1024, AMDGPU_GEM_DOMAIN_GTT,152AMDGPU_GEM_DOMAIN_VRAM);153if (r)154goto done;155r = amdgpu_benchmark_move(adev, 1024*1024, AMDGPU_GEM_DOMAIN_VRAM,156AMDGPU_GEM_DOMAIN_GTT);157if (r)158goto done;159break;160case 2:161dev_info(adev->dev,162"benchmark test: %d (simple test, VRAM to VRAM)\n",163test_number);164/* simple test, VRAM to VRAM */165r = amdgpu_benchmark_move(adev, 1024*1024, AMDGPU_GEM_DOMAIN_VRAM,166AMDGPU_GEM_DOMAIN_VRAM);167if (r)168goto done;169break;170case 3:171dev_info(adev->dev,172"benchmark test: %d (GTT to VRAM, buffer size sweep, powers of 2)\n",173test_number);174/* GTT to VRAM, buffer size sweep, powers of 2 */175for (i = 1; i <= 16384; i <<= 1) {176r = amdgpu_benchmark_move(adev, i * AMDGPU_GPU_PAGE_SIZE,177AMDGPU_GEM_DOMAIN_GTT,178AMDGPU_GEM_DOMAIN_VRAM);179if (r)180goto done;181}182break;183case 4:184dev_info(adev->dev,185"benchmark test: %d (VRAM to GTT, buffer size sweep, powers of 2)\n",186test_number);187/* VRAM to GTT, buffer size sweep, powers of 2 */188for (i = 1; i <= 16384; i <<= 1) {189r = amdgpu_benchmark_move(adev, i * AMDGPU_GPU_PAGE_SIZE,190AMDGPU_GEM_DOMAIN_VRAM,191AMDGPU_GEM_DOMAIN_GTT);192if (r)193goto done;194}195break;196case 5:197dev_info(adev->dev,198"benchmark test: %d (VRAM to VRAM, buffer size sweep, powers of 2)\n",199test_number);200/* VRAM to VRAM, buffer size sweep, powers of 2 */201for (i = 1; i <= 16384; i <<= 1) {202r = amdgpu_benchmark_move(adev, i * AMDGPU_GPU_PAGE_SIZE,203AMDGPU_GEM_DOMAIN_VRAM,204AMDGPU_GEM_DOMAIN_VRAM);205if (r)206goto done;207}208break;209case 6:210dev_info(adev->dev,211"benchmark test: %d (GTT to VRAM, buffer size sweep, common modes)\n",212test_number);213/* GTT to VRAM, buffer size sweep, common modes */214for (i = 0; i < AMDGPU_BENCHMARK_COMMON_MODES_N; i++) {215r = amdgpu_benchmark_move(adev, common_modes[i],216AMDGPU_GEM_DOMAIN_GTT,217AMDGPU_GEM_DOMAIN_VRAM);218if (r)219goto done;220}221break;222case 7:223dev_info(adev->dev,224"benchmark test: %d (VRAM to GTT, buffer size sweep, common modes)\n",225test_number);226/* VRAM to GTT, buffer size sweep, common modes */227for (i = 0; i < AMDGPU_BENCHMARK_COMMON_MODES_N; i++) {228r = amdgpu_benchmark_move(adev, common_modes[i],229AMDGPU_GEM_DOMAIN_VRAM,230AMDGPU_GEM_DOMAIN_GTT);231if (r)232goto done;233}234break;235case 8:236dev_info(adev->dev,237"benchmark test: %d (VRAM to VRAM, buffer size sweep, common modes)\n",238test_number);239/* VRAM to VRAM, buffer size sweep, common modes */240for (i = 0; i < AMDGPU_BENCHMARK_COMMON_MODES_N; i++) {241r = amdgpu_benchmark_move(adev, common_modes[i],242AMDGPU_GEM_DOMAIN_VRAM,243AMDGPU_GEM_DOMAIN_VRAM);244if (r)245goto done;246}247break;248249default:250dev_info(adev->dev, "Unknown benchmark %d\n", test_number);251r = -EINVAL;252break;253}254255done:256mutex_unlock(&adev->benchmark_mutex);257258return r;259}260261262