@@ -1805,7 +1805,7 @@ struct drm_i915_private {
/*
* Lock associated with adding/modifying/removing OA configs
- * in dev_priv->perf.metrics_idr.
+ * in dev_priv->perf.configs.
*/
struct mutex metrics_lock;
@@ -1813,7 +1813,7 @@ struct drm_i915_private {
* List of dynamic configurations, you need to hold
* dev_priv->perf.metrics_lock to access it.
*/
- struct idr metrics_idr;
+ struct xarray configs;
/*
* Lock associated with anything below within this structure
@@ -400,7 +400,7 @@ static int get_oa_config(struct drm_i915_private *dev_priv,
if (ret)
return ret;
- *out_config = idr_find(&dev_priv->perf.metrics_idr, metrics_set);
+ *out_config = xa_load(&dev_priv->perf.configs, metrics_set);
if (!*out_config)
ret = -EINVAL;
else
@@ -3142,7 +3142,8 @@ int i915_perf_add_config_ioctl(struct drm_device *dev, void *data,
struct drm_i915_private *dev_priv = dev->dev_private;
struct drm_i915_perf_oa_config *args = data;
struct i915_oa_config *oa_config, *tmp;
- int err, id;
+ unsigned long id;
+ int err;
if (!dev_priv->perf.initialized) {
DRM_DEBUG("i915 perf interface not available for this system\n");
@@ -3238,7 +3239,7 @@ int i915_perf_add_config_ioctl(struct drm_device *dev, void *data,
/* We shouldn't have too many configs, so this iteration shouldn't be
* too costly.
*/
- idr_for_each_entry(&dev_priv->perf.metrics_idr, tmp, id) {
+ xa_for_each(&dev_priv->perf.configs, id, tmp) {
if (!strcmp(tmp->uuid, oa_config->uuid)) {
DRM_DEBUG("OA config already exists with this uuid\n");
err = -EADDRINUSE;
@@ -3253,12 +3254,10 @@ int i915_perf_add_config_ioctl(struct drm_device *dev, void *data,
}
/* Config id 0 is invalid, id 1 for kernel stored test config. */
- oa_config->id = idr_alloc(&dev_priv->perf.metrics_idr,
- oa_config, 2,
- 0, GFP_KERNEL);
- if (oa_config->id < 0) {
+ err = xa_alloc(&dev_priv->perf.configs, &oa_config->id, oa_config,
+ XA_LIMIT(2, UINT_MAX), GFP_KERNEL);
+ if (err < 0) {
DRM_DEBUG("Failed to create sysfs entry for OA config\n");
- err = oa_config->id;
goto sysfs_err;
}
@@ -3309,7 +3308,7 @@ int i915_perf_remove_config_ioctl(struct drm_device *dev, void *data,
if (ret)
goto lock_err;
- oa_config = idr_find(&dev_priv->perf.metrics_idr, *arg);
+ oa_config = xa_erase(&dev_priv->perf.configs, *arg);
if (!oa_config) {
DRM_DEBUG("Failed to remove unknown OA config\n");
ret = -ENOENT;
@@ -3321,8 +3320,6 @@ int i915_perf_remove_config_ioctl(struct drm_device *dev, void *data,
sysfs_remove_group(dev_priv->perf.metrics_kobj,
&oa_config->sysfs_metric);
- idr_remove(&dev_priv->perf.metrics_idr, *arg);
-
DRM_DEBUG("Removed config %s id=%i\n", oa_config->uuid, oa_config->id);
put_oa_config(dev_priv, oa_config);
@@ -3475,33 +3472,27 @@ void i915_perf_init(struct drm_i915_private *dev_priv)
dev_priv->perf.sysctl_header = register_sysctl_table(dev_root);
mutex_init(&dev_priv->perf.metrics_lock);
- idr_init(&dev_priv->perf.metrics_idr);
+ xa_init_flags(&dev_priv->perf.configs, XA_FLAGS_ALLOC);
dev_priv->perf.initialized = true;
}
}
-static int destroy_config(int id, void *p, void *data)
-{
- struct drm_i915_private *dev_priv = data;
- struct i915_oa_config *oa_config = p;
-
- put_oa_config(dev_priv, oa_config);
-
- return 0;
-}
-
/**
* i915_perf_fini - Counter part to i915_perf_init()
* @dev_priv: i915 device instance
*/
void i915_perf_fini(struct drm_i915_private *dev_priv)
{
+ struct i915_oa_config *oa_config;
+ unsigned long index;
+
if (!dev_priv->perf.initialized)
return;
- idr_for_each(&dev_priv->perf.metrics_idr, destroy_config, dev_priv);
- idr_destroy(&dev_priv->perf.metrics_idr);
+ xa_for_each(&dev_priv->perf.configs, index, oa_config)
+ put_oa_config(dev_priv, oa_config);
+ xa_destroy(&dev_priv->perf.configs);
unregister_sysctl_table(dev_priv->perf.sysctl_header);
Signed-off-by: Matthew Wilcox <willy@infradead.org> --- drivers/gpu/drm/i915/i915_drv.h | 4 ++-- drivers/gpu/drm/i915/i915_perf.c | 39 ++++++++++++-------------------- 2 files changed, 17 insertions(+), 26 deletions(-)