Commit 71ccf2a0 authored by Ben Skeggs's avatar Ben Skeggs

drm/nouveau/engine: use refcount_t + private mutex

nvkm_subdev.mutex is going away.
Signed-off-by: default avatarBen Skeggs <bskeggs@redhat.com>
Reviewed-by: default avatarLyude Paul <lyude@redhat.com>
parent 4c3a3292
...@@ -11,7 +11,11 @@ struct nvkm_engine { ...@@ -11,7 +11,11 @@ struct nvkm_engine {
struct nvkm_subdev subdev; struct nvkm_subdev subdev;
spinlock_t lock; spinlock_t lock;
int usecount; struct {
refcount_t refcount;
struct mutex mutex;
bool enabled;
} use;
}; };
struct nvkm_engine_func { struct nvkm_engine_func {
......
...@@ -40,10 +40,11 @@ nvkm_engine_unref(struct nvkm_engine **pengine) ...@@ -40,10 +40,11 @@ nvkm_engine_unref(struct nvkm_engine **pengine)
{ {
struct nvkm_engine *engine = *pengine; struct nvkm_engine *engine = *pengine;
if (engine) { if (engine) {
mutex_lock(&engine->subdev.mutex); if (refcount_dec_and_mutex_lock(&engine->use.refcount, &engine->use.mutex)) {
if (--engine->usecount == 0)
nvkm_subdev_fini(&engine->subdev, false); nvkm_subdev_fini(&engine->subdev, false);
mutex_unlock(&engine->subdev.mutex); engine->use.enabled = false;
mutex_unlock(&engine->use.mutex);
}
*pengine = NULL; *pengine = NULL;
} }
} }
...@@ -51,17 +52,21 @@ nvkm_engine_unref(struct nvkm_engine **pengine) ...@@ -51,17 +52,21 @@ nvkm_engine_unref(struct nvkm_engine **pengine)
struct nvkm_engine * struct nvkm_engine *
nvkm_engine_ref(struct nvkm_engine *engine) nvkm_engine_ref(struct nvkm_engine *engine)
{ {
int ret;
if (engine) { if (engine) {
mutex_lock(&engine->subdev.mutex); if (!refcount_inc_not_zero(&engine->use.refcount)) {
if (++engine->usecount == 1) { mutex_lock(&engine->use.mutex);
int ret = nvkm_subdev_init(&engine->subdev); if (!refcount_inc_not_zero(&engine->use.refcount)) {
if (ret) { engine->use.enabled = true;
engine->usecount--; if ((ret = nvkm_subdev_init(&engine->subdev))) {
mutex_unlock(&engine->subdev.mutex); engine->use.enabled = false;
return ERR_PTR(ret); mutex_unlock(&engine->use.mutex);
return ERR_PTR(ret);
}
refcount_set(&engine->use.refcount, 1);
} }
mutex_unlock(&engine->use.mutex);
} }
mutex_unlock(&engine->subdev.mutex);
} }
return engine; return engine;
} }
...@@ -114,7 +119,7 @@ nvkm_engine_init(struct nvkm_subdev *subdev) ...@@ -114,7 +119,7 @@ nvkm_engine_init(struct nvkm_subdev *subdev)
int ret = 0, i; int ret = 0, i;
s64 time; s64 time;
if (!engine->usecount) { if (!engine->use.enabled) {
nvkm_trace(subdev, "init skipped, engine has no users\n"); nvkm_trace(subdev, "init skipped, engine has no users\n");
return ret; return ret;
} }
...@@ -156,6 +161,7 @@ nvkm_engine_dtor(struct nvkm_subdev *subdev) ...@@ -156,6 +161,7 @@ nvkm_engine_dtor(struct nvkm_subdev *subdev)
struct nvkm_engine *engine = nvkm_engine(subdev); struct nvkm_engine *engine = nvkm_engine(subdev);
if (engine->func->dtor) if (engine->func->dtor)
return engine->func->dtor(engine); return engine->func->dtor(engine);
mutex_destroy(&engine->use.mutex);
return engine; return engine;
} }
...@@ -176,6 +182,8 @@ nvkm_engine_ctor(const struct nvkm_engine_func *func, ...@@ -176,6 +182,8 @@ nvkm_engine_ctor(const struct nvkm_engine_func *func,
{ {
nvkm_subdev_ctor(&nvkm_engine_func, device, index, &engine->subdev); nvkm_subdev_ctor(&nvkm_engine_func, device, index, &engine->subdev);
engine->func = func; engine->func = func;
refcount_set(&engine->use.refcount, 0);
mutex_init(&engine->use.mutex);
if (!nvkm_boolopt(device->cfgopt, nvkm_subdev_name[index], enable)) { if (!nvkm_boolopt(device->cfgopt, nvkm_subdev_name[index], enable)) {
nvkm_debug(&engine->subdev, "disabled\n"); nvkm_debug(&engine->subdev, "disabled\n");
......
Markdown is supported
0%
or
You are about to add 0 people to the discussion. Proceed with caution.
Finish editing this message first!
Please register or to comment