File Index
Files and directories
Sign in
FILE

radeon_kms.c

File preview with syntax highlighting.

linux-6.19.14/drivers/gpu/drm/radeon/radeon_kms.c C
  1/*
  2 * Copyright 2008 Advanced Micro Devices, Inc.
  3 * Copyright 2008 Red Hat Inc.
  4 * Copyright 2009 Jerome Glisse.
  5 *
  6 * Permission is hereby granted, free of charge, to any person obtaining a
  7 * copy of this software and associated documentation files (the "Software"),
  8 * to deal in the Software without restriction, including without limitation
  9 * the rights to use, copy, modify, merge, publish, distribute, sublicense,
 10 * and/or sell copies of the Software, and to permit persons to whom the
 11 * Software is furnished to do so, subject to the following conditions:
 12 *
 13 * The above copyright notice and this permission notice shall be included in
 14 * all copies or substantial portions of the Software.
 15 *
 16 * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
 17 * IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
 18 * FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT.  IN NO EVENT SHALL
 19 * THE COPYRIGHT HOLDER(S) OR AUTHOR(S) BE LIABLE FOR ANY CLAIM, DAMAGES OR
 20 * OTHER LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE,
 21 * ARISING FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR
 22 * OTHER DEALINGS IN THE SOFTWARE.
 23 *
 24 * Authors: Dave Airlie
 25 *          Alex Deucher
 26 *          Jerome Glisse
 27 */
 28
 29#include <linux/pci.h>
 30#include <linux/pm_runtime.h>
 31#include <linux/slab.h>
 32#include <linux/uaccess.h>
 33#include <linux/vga_switcheroo.h>
 34
 35#include <drm/drm_file.h>
 36#include <drm/drm_ioctl.h>
 37#include <drm/radeon_drm.h>
 38
 39#include "radeon.h"
 40#include "radeon_asic.h"
 41#include "radeon_drv.h"
 42#include "radeon_kms.h"
 43
 44#if defined(CONFIG_VGA_SWITCHEROO)
 45bool radeon_has_atpx(void);
 46#else
 47static inline bool radeon_has_atpx(void) { return false; }
 48#endif
 49
 50/**
 51 * radeon_driver_unload_kms - Main unload function for KMS.
 52 *
 53 * @dev: drm dev pointer
 54 *
 55 * This is the main unload function for KMS (all asics).
 56 * It calls radeon_modeset_fini() to tear down the
 57 * displays, and radeon_device_fini() to tear down
 58 * the rest of the device (CP, writeback, etc.).
 59 * Returns 0 on success.
 60 */
 61void radeon_driver_unload_kms(struct drm_device *dev)
 62{
 63	struct radeon_device *rdev = dev->dev_private;
 64
 65	if (rdev == NULL)
 66		return;
 67
 68	if (rdev->rmmio == NULL)
 69		goto done_free;
 70
 71	if (radeon_is_px(dev)) {
 72		pm_runtime_get_sync(dev->dev);
 73		pm_runtime_forbid(dev->dev);
 74	}
 75
 76	radeon_acpi_fini(rdev);
 77
 78	radeon_modeset_fini(rdev);
 79	radeon_device_fini(rdev);
 80
 81	if (rdev->agp)
 82		arch_phys_wc_del(rdev->agp->agp_mtrr);
 83	kfree(rdev->agp);
 84	rdev->agp = NULL;
 85
 86done_free:
 87	dev->dev_private = NULL;
 88}
 89
 90/**
 91 * radeon_driver_load_kms - Main load function for KMS.
 92 *
 93 * @dev: drm dev pointer
 94 * @flags: device flags
 95 *
 96 * This is the main load function for KMS (all asics).
 97 * It calls radeon_device_init() to set up the non-display
 98 * parts of the chip (asic init, CP, writeback, etc.), and
 99 * radeon_modeset_init() to set up the display parts
100 * (crtcs, encoders, hotplug detect, etc.).
101 * Returns 0 on success, error on failure.
102 */
103int radeon_driver_load_kms(struct drm_device *dev, unsigned long flags)
104{
105	struct pci_dev *pdev = to_pci_dev(dev->dev);
106	struct radeon_device *rdev = dev->dev_private;
107	int r, acpi_status;
108
109#ifdef __alpha__
110	rdev->hose = pdev->sysdata;
111#endif
112
113	if (pci_find_capability(pdev, PCI_CAP_ID_AGP))
114		rdev->agp = radeon_agp_head_init(dev);
115	if (rdev->agp) {
116		rdev->agp->agp_mtrr = arch_phys_wc_add(
117			rdev->agp->agp_info.aper_base,
118			rdev->agp->agp_info.aper_size *
119			1024 * 1024);
120	}
121
122	/* update BUS flag */
123	if (pci_find_capability(pdev, PCI_CAP_ID_AGP)) {
124		flags |= RADEON_IS_AGP;
125	} else if (pci_is_pcie(pdev)) {
126		flags |= RADEON_IS_PCIE;
127	} else {
128		flags |= RADEON_IS_PCI;
129	}
130
131	if ((radeon_runtime_pm != 0) &&
132	    radeon_has_atpx() &&
133	    ((flags & RADEON_IS_IGP) == 0) &&
134	    !pci_is_thunderbolt_attached(pdev))
135		flags |= RADEON_IS_PX;
136
137	/* radeon_device_init should report only fatal error
138	 * like memory allocation failure or iomapping failure,
139	 * or memory manager initialization failure, it must
140	 * properly initialize the GPU MC controller and permit
141	 * VRAM allocation
142	 */
143	r = radeon_device_init(rdev, dev, pdev, flags);
144	if (r) {
145		dev_err(dev->dev, "Fatal error during GPU init\n");
146		goto out;
147	}
148
149	/* Again modeset_init should fail only on fatal error
150	 * otherwise it should provide enough functionalities
151	 * for shadowfb to run
152	 */
153	r = radeon_modeset_init(rdev);
154	if (r)
155		dev_err(dev->dev, "Fatal error during modeset init\n");
156
157	/* Call ACPI methods: require modeset init
158	 * but failure is not fatal
159	 */
160	if (!r) {
161		acpi_status = radeon_acpi_init(rdev);
162		if (acpi_status)
163			dev_dbg(dev->dev, "Error during ACPI methods call\n");
164	}
165
166	if (radeon_is_px(dev)) {
167		dev_pm_set_driver_flags(dev->dev, DPM_FLAG_NO_DIRECT_COMPLETE);
168		pm_runtime_use_autosuspend(dev->dev);
169		pm_runtime_set_autosuspend_delay(dev->dev, 5000);
170		pm_runtime_set_active(dev->dev);
171		pm_runtime_allow(dev->dev);
172		pm_runtime_put_autosuspend(dev->dev);
173	}
174
175out:
176	if (r)
177		radeon_driver_unload_kms(dev);
178
179
180	return r;
181}
182
183/**
184 * radeon_set_filp_rights - Set filp right.
185 *
186 * @dev: drm dev pointer
187 * @owner: drm file
188 * @applier: drm file
189 * @value: value
190 *
191 * Sets the filp rights for the device (all asics).
192 */
193static void radeon_set_filp_rights(struct drm_device *dev,
194				   struct drm_file **owner,
195				   struct drm_file *applier,
196				   uint32_t *value)
197{
198	struct radeon_device *rdev = dev->dev_private;
199
200	mutex_lock(&rdev->gem.mutex);
201	if (*value == 1) {
202		/* wants rights */
203		if (!*owner)
204			*owner = applier;
205	} else if (*value == 0) {
206		/* revokes rights */
207		if (*owner == applier)
208			*owner = NULL;
209	}
210	*value = *owner == applier ? 1 : 0;
211	mutex_unlock(&rdev->gem.mutex);
212}
213
214/*
215 * Userspace get information ioctl
216 */
217/**
218 * radeon_info_ioctl - answer a device specific request.
219 *
220 * @dev: drm device pointer
221 * @data: request object
222 * @filp: drm filp
223 *
224 * This function is used to pass device specific parameters to the userspace
225 * drivers.  Examples include: pci device id, pipeline parms, tiling params,
226 * etc. (all asics).
227 * Returns 0 on success, -EINVAL on failure.
228 */
229int radeon_info_ioctl(struct drm_device *dev, void *data, struct drm_file *filp)
230{
231	struct radeon_device *rdev = dev->dev_private;
232	struct drm_radeon_info *info = data;
233	struct radeon_mode_info *minfo = &rdev->mode_info;
234	uint32_t *value, value_tmp, *value_ptr, value_size;
235	struct ttm_resource_manager *man;
236	uint64_t value64;
237	struct drm_crtc *crtc;
238	int i, found;
239
240	value_ptr = (uint32_t *)((unsigned long)info->value);
241	value = &value_tmp;
242	value_size = sizeof(uint32_t);
243
244	switch (info->request) {
245	case RADEON_INFO_DEVICE_ID:
246		*value = to_pci_dev(dev->dev)->device;
247		break;
248	case RADEON_INFO_NUM_GB_PIPES:
249		*value = rdev->num_gb_pipes;
250		break;
251	case RADEON_INFO_NUM_Z_PIPES:
252		*value = rdev->num_z_pipes;
253		break;
254	case RADEON_INFO_ACCEL_WORKING:
255		/* xf86-video-ati 6.13.0 relies on this being false for evergreen */
256		if ((rdev->family >= CHIP_CEDAR) && (rdev->family <= CHIP_HEMLOCK))
257			*value = false;
258		else
259			*value = rdev->accel_working;
260		break;
261	case RADEON_INFO_CRTC_FROM_ID:
262		if (copy_from_user(value, value_ptr, sizeof(uint32_t))) {
263			DRM_ERROR("copy_from_user %s:%u\n", __func__, __LINE__);
264			return -EFAULT;
265		}
266		for (i = 0, found = 0; i < rdev->num_crtc; i++) {
267			crtc = (struct drm_crtc *)minfo->crtcs[i];
268			if (crtc && crtc->base.id == *value) {
269				struct radeon_crtc *radeon_crtc = to_radeon_crtc(crtc);
270				*value = radeon_crtc->crtc_id;
271				found = 1;
272				break;
273			}
274		}
275		if (!found) {
276			DRM_DEBUG_KMS("unknown crtc id %d\n", *value);
277			return -EINVAL;
278		}
279		break;
280	case RADEON_INFO_ACCEL_WORKING2:
281		if (rdev->family == CHIP_HAWAII) {
282			if (rdev->accel_working) {
283				if (rdev->new_fw)
284					*value = 3;
285				else
286					*value = 2;
287			} else {
288				*value = 0;
289			}
290		} else {
291			*value = rdev->accel_working;
292		}
293		break;
294	case RADEON_INFO_TILING_CONFIG:
295		if (rdev->family >= CHIP_BONAIRE)
296			*value = rdev->config.cik.tile_config;
297		else if (rdev->family >= CHIP_TAHITI)
298			*value = rdev->config.si.tile_config;
299		else if (rdev->family >= CHIP_CAYMAN)
300			*value = rdev->config.cayman.tile_config;
301		else if (rdev->family >= CHIP_CEDAR)
302			*value = rdev->config.evergreen.tile_config;
303		else if (rdev->family >= CHIP_RV770)
304			*value = rdev->config.rv770.tile_config;
305		else if (rdev->family >= CHIP_R600)
306			*value = rdev->config.r600.tile_config;
307		else {
308			DRM_DEBUG_KMS("tiling config is r6xx+ only!\n");
309			return -EINVAL;
310		}
311		break;
312	case RADEON_INFO_WANT_HYPERZ:
313		/* The "value" here is both an input and output parameter.
314		 * If the input value is 1, filp requests hyper-z access.
315		 * If the input value is 0, filp revokes its hyper-z access.
316		 *
317		 * When returning, the value is 1 if filp owns hyper-z access,
318		 * 0 otherwise. */
319		if (copy_from_user(value, value_ptr, sizeof(uint32_t))) {
320			DRM_ERROR("copy_from_user %s:%u\n", __func__, __LINE__);
321			return -EFAULT;
322		}
323		if (*value >= 2) {
324			DRM_DEBUG_KMS("WANT_HYPERZ: invalid value %d\n", *value);
325			return -EINVAL;
326		}
327		radeon_set_filp_rights(dev, &rdev->hyperz_filp, filp, value);
328		break;
329	case RADEON_INFO_WANT_CMASK:
330		/* The same logic as Hyper-Z. */
331		if (copy_from_user(value, value_ptr, sizeof(uint32_t))) {
332			DRM_ERROR("copy_from_user %s:%u\n", __func__, __LINE__);
333			return -EFAULT;
334		}
335		if (*value >= 2) {
336			DRM_DEBUG_KMS("WANT_CMASK: invalid value %d\n", *value);
337			return -EINVAL;
338		}
339		radeon_set_filp_rights(dev, &rdev->cmask_filp, filp, value);
340		break;
341	case RADEON_INFO_CLOCK_CRYSTAL_FREQ:
342		/* return clock value in KHz */
343		if (rdev->asic->get_xclk)
344			*value = radeon_get_xclk(rdev) * 10;
345		else
346			*value = rdev->clock.spll.reference_freq * 10;
347		break;
348	case RADEON_INFO_NUM_BACKENDS:
349		if (rdev->family >= CHIP_BONAIRE)
350			*value = rdev->config.cik.max_backends_per_se *
351				rdev->config.cik.max_shader_engines;
352		else if (rdev->family >= CHIP_TAHITI)
353			*value = rdev->config.si.max_backends_per_se *
354				rdev->config.si.max_shader_engines;
355		else if (rdev->family >= CHIP_CAYMAN)
356			*value = rdev->config.cayman.max_backends_per_se *
357				rdev->config.cayman.max_shader_engines;
358		else if (rdev->family >= CHIP_CEDAR)
359			*value = rdev->config.evergreen.max_backends;
360		else if (rdev->family >= CHIP_RV770)
361			*value = rdev->config.rv770.max_backends;
362		else if (rdev->family >= CHIP_R600)
363			*value = rdev->config.r600.max_backends;
364		else {
365			return -EINVAL;
366		}
367		break;
368	case RADEON_INFO_NUM_TILE_PIPES:
369		if (rdev->family >= CHIP_BONAIRE)
370			*value = rdev->config.cik.max_tile_pipes;
371		else if (rdev->family >= CHIP_TAHITI)
372			*value = rdev->config.si.max_tile_pipes;
373		else if (rdev->family >= CHIP_CAYMAN)
374			*value = rdev->config.cayman.max_tile_pipes;
375		else if (rdev->family >= CHIP_CEDAR)
376			*value = rdev->config.evergreen.max_tile_pipes;
377		else if (rdev->family >= CHIP_RV770)
378			*value = rdev->config.rv770.max_tile_pipes;
379		else if (rdev->family >= CHIP_R600)
380			*value = rdev->config.r600.max_tile_pipes;
381		else {
382			return -EINVAL;
383		}
384		break;
385	case RADEON_INFO_FUSION_GART_WORKING:
386		*value = 1;
387		break;
388	case RADEON_INFO_BACKEND_MAP:
389		if (rdev->family >= CHIP_BONAIRE)
390			*value = rdev->config.cik.backend_map;
391		else if (rdev->family >= CHIP_TAHITI)
392			*value = rdev->config.si.backend_map;
393		else if (rdev->family >= CHIP_CAYMAN)
394			*value = rdev->config.cayman.backend_map;
395		else if (rdev->family >= CHIP_CEDAR)
396			*value = rdev->config.evergreen.backend_map;
397		else if (rdev->family >= CHIP_RV770)
398			*value = rdev->config.rv770.backend_map;
399		else if (rdev->family >= CHIP_R600)
400			*value = rdev->config.r600.backend_map;
401		else {
402			return -EINVAL;
403		}
404		break;
405	case RADEON_INFO_VA_START:
406		/* this is where we report if vm is supported or not */
407		if (rdev->family < CHIP_CAYMAN)
408			return -EINVAL;
409		*value = RADEON_VA_RESERVED_SIZE;
410		break;
411	case RADEON_INFO_IB_VM_MAX_SIZE:
412		/* this is where we report if vm is supported or not */
413		if (rdev->family < CHIP_CAYMAN)
414			return -EINVAL;
415		*value = RADEON_IB_VM_MAX_SIZE;
416		break;
417	case RADEON_INFO_MAX_PIPES:
418		if (rdev->family >= CHIP_BONAIRE)
419			*value = rdev->config.cik.max_cu_per_sh;
420		else if (rdev->family >= CHIP_TAHITI)
421			*value = rdev->config.si.max_cu_per_sh;
422		else if (rdev->family >= CHIP_CAYMAN)
423			*value = rdev->config.cayman.max_pipes_per_simd;
424		else if (rdev->family >= CHIP_CEDAR)
425			*value = rdev->config.evergreen.max_pipes;
426		else if (rdev->family >= CHIP_RV770)
427			*value = rdev->config.rv770.max_pipes;
428		else if (rdev->family >= CHIP_R600)
429			*value = rdev->config.r600.max_pipes;
430		else {
431			return -EINVAL;
432		}
433		break;
434	case RADEON_INFO_TIMESTAMP:
435		if (rdev->family < CHIP_R600) {
436			DRM_DEBUG_KMS("timestamp is r6xx+ only!\n");
437			return -EINVAL;
438		}
439		value = (uint32_t *)&value64;
440		value_size = sizeof(uint64_t);
441		value64 = radeon_get_gpu_clock_counter(rdev);
442		break;
443	case RADEON_INFO_MAX_SE:
444		if (rdev->family >= CHIP_BONAIRE)
445			*value = rdev->config.cik.max_shader_engines;
446		else if (rdev->family >= CHIP_TAHITI)
447			*value = rdev->config.si.max_shader_engines;
448		else if (rdev->family >= CHIP_CAYMAN)
449			*value = rdev->config.cayman.max_shader_engines;
450		else if (rdev->family >= CHIP_CEDAR)
451			*value = rdev->config.evergreen.num_ses;
452		else
453			*value = 1;
454		break;
455	case RADEON_INFO_MAX_SH_PER_SE:
456		if (rdev->family >= CHIP_BONAIRE)
457			*value = rdev->config.cik.max_sh_per_se;
458		else if (rdev->family >= CHIP_TAHITI)
459			*value = rdev->config.si.max_sh_per_se;
460		else
461			return -EINVAL;
462		break;
463	case RADEON_INFO_FASTFB_WORKING:
464		*value = rdev->fastfb_working;
465		break;
466	case RADEON_INFO_RING_WORKING:
467		if (copy_from_user(value, value_ptr, sizeof(uint32_t))) {
468			DRM_ERROR("copy_from_user %s:%u\n", __func__, __LINE__);
469			return -EFAULT;
470		}
471		switch (*value) {
472		case RADEON_CS_RING_GFX:
473		case RADEON_CS_RING_COMPUTE:
474			*value = rdev->ring[RADEON_RING_TYPE_GFX_INDEX].ready;
475			break;
476		case RADEON_CS_RING_DMA:
477			*value = rdev->ring[R600_RING_TYPE_DMA_INDEX].ready;
478			*value |= rdev->ring[CAYMAN_RING_TYPE_DMA1_INDEX].ready;
479			break;
480		case RADEON_CS_RING_UVD:
481			*value = rdev->ring[R600_RING_TYPE_UVD_INDEX].ready;
482			break;
483		case RADEON_CS_RING_VCE:
484			*value = rdev->ring[TN_RING_TYPE_VCE1_INDEX].ready;
485			break;
486		default:
487			return -EINVAL;
488		}
489		break;
490	case RADEON_INFO_SI_TILE_MODE_ARRAY:
491		if (rdev->family >= CHIP_BONAIRE) {
492			value = rdev->config.cik.tile_mode_array;
493			value_size = sizeof(uint32_t)*32;
494		} else if (rdev->family >= CHIP_TAHITI) {
495			value = rdev->config.si.tile_mode_array;
496			value_size = sizeof(uint32_t)*32;
497		} else {
498			DRM_DEBUG_KMS("tile mode array is si+ only!\n");
499			return -EINVAL;
500		}
501		break;
502	case RADEON_INFO_CIK_MACROTILE_MODE_ARRAY:
503		if (rdev->family >= CHIP_BONAIRE) {
504			value = rdev->config.cik.macrotile_mode_array;
505			value_size = sizeof(uint32_t)*16;
506		} else {
507			DRM_DEBUG_KMS("macrotile mode array is cik+ only!\n");
508			return -EINVAL;
509		}
510		break;
511	case RADEON_INFO_SI_CP_DMA_COMPUTE:
512		*value = 1;
513		break;
514	case RADEON_INFO_SI_BACKEND_ENABLED_MASK:
515		if (rdev->family >= CHIP_BONAIRE) {
516			*value = rdev->config.cik.backend_enable_mask;
517		} else if (rdev->family >= CHIP_TAHITI) {
518			*value = rdev->config.si.backend_enable_mask;
519		} else {
520			DRM_DEBUG_KMS("BACKEND_ENABLED_MASK is si+ only!\n");
521			return -EINVAL;
522		}
523		break;
524	case RADEON_INFO_MAX_SCLK:
525		if ((rdev->pm.pm_method == PM_METHOD_DPM) &&
526		    rdev->pm.dpm_enabled)
527			*value = rdev->pm.dpm.dyn_state.max_clock_voltage_on_ac.sclk * 10;
528		else
529			*value = rdev->pm.default_sclk * 10;
530		break;
531	case RADEON_INFO_VCE_FW_VERSION:
532		*value = rdev->vce.fw_version;
533		break;
534	case RADEON_INFO_VCE_FB_VERSION:
535		*value = rdev->vce.fb_version;
536		break;
537	case RADEON_INFO_NUM_BYTES_MOVED:
538		value = (uint32_t *)&value64;
539		value_size = sizeof(uint64_t);
540		value64 = atomic64_read(&rdev->num_bytes_moved);
541		break;
542	case RADEON_INFO_VRAM_USAGE:
543		value = (uint32_t *)&value64;
544		value_size = sizeof(uint64_t);
545		man = ttm_manager_type(&rdev->mman.bdev, TTM_PL_VRAM);
546		value64 = ttm_resource_manager_usage(man);
547		break;
548	case RADEON_INFO_GTT_USAGE:
549		value = (uint32_t *)&value64;
550		value_size = sizeof(uint64_t);
551		man = ttm_manager_type(&rdev->mman.bdev, TTM_PL_TT);
552		value64 = ttm_resource_manager_usage(man);
553		break;
554	case RADEON_INFO_ACTIVE_CU_COUNT:
555		if (rdev->family >= CHIP_BONAIRE)
556			*value = rdev->config.cik.active_cus;
557		else if (rdev->family >= CHIP_TAHITI)
558			*value = rdev->config.si.active_cus;
559		else if (rdev->family >= CHIP_CAYMAN)
560			*value = rdev->config.cayman.active_simds;
561		else if (rdev->family >= CHIP_CEDAR)
562			*value = rdev->config.evergreen.active_simds;
563		else if (rdev->family >= CHIP_RV770)
564			*value = rdev->config.rv770.active_simds;
565		else if (rdev->family >= CHIP_R600)
566			*value = rdev->config.r600.active_simds;
567		else
568			*value = 1;
569		break;
570	case RADEON_INFO_CURRENT_GPU_TEMP:
571		/* get temperature in millidegrees C */
572		if (rdev->asic->pm.get_temperature)
573			*value = radeon_get_temperature(rdev);
574		else
575			*value = 0;
576		break;
577	case RADEON_INFO_CURRENT_GPU_SCLK:
578		/* get sclk in Mhz */
579		if (rdev->pm.dpm_enabled)
580			*value = radeon_dpm_get_current_sclk(rdev) / 100;
581		else
582			*value = rdev->pm.current_sclk / 100;
583		break;
584	case RADEON_INFO_CURRENT_GPU_MCLK:
585		/* get mclk in Mhz */
586		if (rdev->pm.dpm_enabled)
587			*value = radeon_dpm_get_current_mclk(rdev) / 100;
588		else
589			*value = rdev->pm.current_mclk / 100;
590		break;
591	case RADEON_INFO_READ_REG:
592		if (copy_from_user(value, value_ptr, sizeof(uint32_t))) {
593			DRM_ERROR("copy_from_user %s:%u\n", __func__, __LINE__);
594			return -EFAULT;
595		}
596		if (radeon_get_allowed_info_register(rdev, *value, value))
597			return -EINVAL;
598		break;
599	case RADEON_INFO_VA_UNMAP_WORKING:
600		*value = true;
601		break;
602	case RADEON_INFO_GPU_RESET_COUNTER:
603		*value = atomic_read(&rdev->gpu_reset_counter);
604		break;
605	default:
606		DRM_DEBUG_KMS("Invalid request %d\n", info->request);
607		return -EINVAL;
608	}
609	if (copy_to_user(value_ptr, (char *)value, value_size)) {
610		DRM_ERROR("copy_to_user %s:%u\n", __func__, __LINE__);
611		return -EFAULT;
612	}
613	return 0;
614}
615
616/**
617 * radeon_driver_open_kms - drm callback for open
618 *
619 * @dev: drm dev pointer
620 * @file_priv: drm file
621 *
622 * On device open, init vm on cayman+ (all asics).
623 * Returns 0 on success, error on failure.
624 */
625int radeon_driver_open_kms(struct drm_device *dev, struct drm_file *file_priv)
626{
627	struct radeon_device *rdev = dev->dev_private;
628	struct radeon_fpriv *fpriv;
629	struct radeon_vm *vm;
630	int r;
631
632	file_priv->driver_priv = NULL;
633
634	r = pm_runtime_get_sync(dev->dev);
635	if (r < 0) {
636		pm_runtime_put_autosuspend(dev->dev);
637		return r;
638	}
639
640	/* new gpu have virtual address space support */
641	if (rdev->family >= CHIP_CAYMAN) {
642
643		fpriv = kzalloc(sizeof(*fpriv), GFP_KERNEL);
644		if (unlikely(!fpriv)) {
645			r = -ENOMEM;
646			goto err_suspend;
647		}
648
649		if (rdev->accel_working) {
650			vm = &fpriv->vm;
651			r = radeon_vm_init(rdev, vm);
652			if (r)
653				goto err_fpriv;
654
655			r = radeon_bo_reserve(rdev->ring_tmp_bo.bo, false);
656			if (r)
657				goto err_vm_fini;
658
659			/* map the ib pool buffer read only into
660			 * virtual address space */
661			vm->ib_bo_va = radeon_vm_bo_add(rdev, vm,
662							rdev->ring_tmp_bo.bo);
663			if (!vm->ib_bo_va) {
664				r = -ENOMEM;
665				goto err_vm_fini;
666			}
667
668			r = radeon_vm_bo_set_addr(rdev, vm->ib_bo_va,
669						  RADEON_VA_IB_OFFSET,
670						  RADEON_VM_PAGE_READABLE |
671						  RADEON_VM_PAGE_SNOOPED);
672			if (r)
673				goto err_vm_fini;
674		}
675		file_priv->driver_priv = fpriv;
676	}
677
678	pm_runtime_put_autosuspend(dev->dev);
679	return 0;
680
681err_vm_fini:
682	radeon_vm_fini(rdev, vm);
683err_fpriv:
684	kfree(fpriv);
685
686err_suspend:
687	pm_runtime_put_autosuspend(dev->dev);
688	return r;
689}
690
691/**
692 * radeon_driver_postclose_kms - drm callback for post close
693 *
694 * @dev: drm dev pointer
695 * @file_priv: drm file
696 *
697 * On device close, tear down hyperz and cmask filps on r1xx-r5xx
698 * (all asics).  And tear down vm on cayman+ (all asics).
699 */
700void radeon_driver_postclose_kms(struct drm_device *dev,
701				 struct drm_file *file_priv)
702{
703	struct radeon_device *rdev = dev->dev_private;
704
705	pm_runtime_get_sync(dev->dev);
706
707	mutex_lock(&rdev->gem.mutex);
708	if (rdev->hyperz_filp == file_priv)
709		rdev->hyperz_filp = NULL;
710	if (rdev->cmask_filp == file_priv)
711		rdev->cmask_filp = NULL;
712	mutex_unlock(&rdev->gem.mutex);
713
714	radeon_uvd_free_handles(rdev, file_priv);
715	radeon_vce_free_handles(rdev, file_priv);
716
717	/* new gpu have virtual address space support */
718	if (rdev->family >= CHIP_CAYMAN && file_priv->driver_priv) {
719		struct radeon_fpriv *fpriv = file_priv->driver_priv;
720		struct radeon_vm *vm = &fpriv->vm;
721		int r;
722
723		if (rdev->accel_working) {
724			r = radeon_bo_reserve(rdev->ring_tmp_bo.bo, false);
725			if (!r) {
726				if (vm->ib_bo_va)
727					radeon_vm_bo_rmv(rdev, vm->ib_bo_va);
728				radeon_bo_unreserve(rdev->ring_tmp_bo.bo);
729			}
730			radeon_vm_fini(rdev, vm);
731		}
732
733		kfree(fpriv);
734		file_priv->driver_priv = NULL;
735	}
736	pm_runtime_put_autosuspend(dev->dev);
737}
738
739/*
740 * VBlank related functions.
741 */
742/**
743 * radeon_get_vblank_counter_kms - get frame count
744 *
745 * @crtc: crtc to get the frame count from
746 *
747 * Gets the frame count on the requested crtc (all asics).
748 * Returns frame count on success, -EINVAL on failure.
749 */
750u32 radeon_get_vblank_counter_kms(struct drm_crtc *crtc)
751{
752	struct drm_device *dev = crtc->dev;
753	unsigned int pipe = crtc->index;
754	int vpos, hpos, stat;
755	u32 count;
756	struct radeon_device *rdev = dev->dev_private;
757
758	if (pipe >= rdev->num_crtc) {
759		DRM_ERROR("Invalid crtc %u\n", pipe);
760		return -EINVAL;
761	}
762
763	/* The hw increments its frame counter at start of vsync, not at start
764	 * of vblank, as is required by DRM core vblank counter handling.
765	 * Cook the hw count here to make it appear to the caller as if it
766	 * incremented at start of vblank. We measure distance to start of
767	 * vblank in vpos. vpos therefore will be >= 0 between start of vblank
768	 * and start of vsync, so vpos >= 0 means to bump the hw frame counter
769	 * result by 1 to give the proper appearance to caller.
770	 */
771	if (rdev->mode_info.crtcs[pipe]) {
772		/* Repeat readout if needed to provide stable result if
773		 * we cross start of vsync during the queries.
774		 */
775		do {
776			count = radeon_get_vblank_counter(rdev, pipe);
777			/* Ask radeon_get_crtc_scanoutpos to return vpos as
778			 * distance to start of vblank, instead of regular
779			 * vertical scanout pos.
780			 */
781			stat = radeon_get_crtc_scanoutpos(
782				dev, pipe, GET_DISTANCE_TO_VBLANKSTART,
783				&vpos, &hpos, NULL, NULL,
784				&rdev->mode_info.crtcs[pipe]->base.hwmode);
785		} while (count != radeon_get_vblank_counter(rdev, pipe));
786
787		if (((stat & (DRM_SCANOUTPOS_VALID | DRM_SCANOUTPOS_ACCURATE)) !=
788		    (DRM_SCANOUTPOS_VALID | DRM_SCANOUTPOS_ACCURATE))) {
789			DRM_DEBUG_VBL("Query failed! stat %d\n", stat);
790		}
791		else {
792			DRM_DEBUG_VBL("crtc %u: dist from vblank start %d\n",
793				      pipe, vpos);
794
795			/* Bump counter if we are at >= leading edge of vblank,
796			 * but before vsync where vpos would turn negative and
797			 * the hw counter really increments.
798			 */
799			if (vpos >= 0)
800				count++;
801		}
802	}
803	else {
804	    /* Fallback to use value as is. */
805	    count = radeon_get_vblank_counter(rdev, pipe);
806	    DRM_DEBUG_VBL("NULL mode info! Returned count may be wrong.\n");
807	}
808
809	return count;
810}
811
812/**
813 * radeon_enable_vblank_kms - enable vblank interrupt
814 *
815 * @crtc: crtc to enable vblank interrupt for
816 *
817 * Enable the interrupt on the requested crtc (all asics).
818 * Returns 0 on success, -EINVAL on failure.
819 */
820int radeon_enable_vblank_kms(struct drm_crtc *crtc)
821{
822	struct drm_device *dev = crtc->dev;
823	unsigned int pipe = crtc->index;
824	struct radeon_device *rdev = dev->dev_private;
825	unsigned long irqflags;
826	int r;
827
828	if (pipe >= rdev->num_crtc) {
829		DRM_ERROR("Invalid crtc %d\n", pipe);
830		return -EINVAL;
831	}
832
833	spin_lock_irqsave(&rdev->irq.lock, irqflags);
834	rdev->irq.crtc_vblank_int[pipe] = true;
835	r = radeon_irq_set(rdev);
836	spin_unlock_irqrestore(&rdev->irq.lock, irqflags);
837	return r;
838}
839
840/**
841 * radeon_disable_vblank_kms - disable vblank interrupt
842 *
843 * @crtc: crtc to disable vblank interrupt for
844 *
845 * Disable the interrupt on the requested crtc (all asics).
846 */
847void radeon_disable_vblank_kms(struct drm_crtc *crtc)
848{
849	struct drm_device *dev = crtc->dev;
850	unsigned int pipe = crtc->index;
851	struct radeon_device *rdev = dev->dev_private;
852	unsigned long irqflags;
853
854	if (pipe >= rdev->num_crtc) {
855		DRM_ERROR("Invalid crtc %d\n", pipe);
856		return;
857	}
858
859	spin_lock_irqsave(&rdev->irq.lock, irqflags);
860	rdev->irq.crtc_vblank_int[pipe] = false;
861	radeon_irq_set(rdev);
862	spin_unlock_irqrestore(&rdev->irq.lock, irqflags);
863}
~/ Read-only file preview.