drm/nouveau/core/object: allow arguments to be passed to map function

MMU will be needing this to specify kind info on BAR mappings.

We have no userspace currently using these interfaces, so break the ABI
instead of supporting both.  NVIF version bump so any future use can be
guarded.

Signed-off-by: Ben Skeggs <bskeggs@redhat.com>
这个提交包含在:
Ben Skeggs
2017-11-01 03:56:19 +10:00
父节点 1f474be9a8
当前提交 0132605039
修改 13 个文件,包含 108 行新增48 行删除

查看文件

@@ -165,47 +165,78 @@ nvif_object_mthd(struct nvif_object *object, u32 mthd, void *data, u32 size)
return ret;
}
void
nvif_object_unmap_handle(struct nvif_object *object)
{
struct {
struct nvif_ioctl_v0 ioctl;
struct nvif_ioctl_unmap unmap;
} args = {
.ioctl.type = NVIF_IOCTL_V0_UNMAP,
};
nvif_object_ioctl(object, &args, sizeof(args), NULL);
}
int
nvif_object_map_handle(struct nvif_object *object, void *argv, u32 argc,
u64 *handle, u64 *length)
{
struct {
struct nvif_ioctl_v0 ioctl;
struct nvif_ioctl_map_v0 map;
} *args;
u32 argn = sizeof(*args) + argc;
int ret, maptype;
if (!(args = kzalloc(argn, GFP_KERNEL)))
return -ENOMEM;
args->ioctl.type = NVIF_IOCTL_V0_MAP;
memcpy(args->map.data, argv, argc);
ret = nvif_object_ioctl(object, args, argn, NULL);
*handle = args->map.handle;
*length = args->map.length;
maptype = args->map.type;
kfree(args);
return ret ? ret : (maptype == NVIF_IOCTL_MAP_V0_IO);
}
void
nvif_object_unmap(struct nvif_object *object)
{
if (object->map.size) {
struct nvif_client *client = object->client;
struct {
struct nvif_ioctl_v0 ioctl;
struct nvif_ioctl_unmap unmap;
} args = {
.ioctl.type = NVIF_IOCTL_V0_UNMAP,
};
if (object->map.ptr) {
struct nvif_client *client = object->client;
if (object->map.ptr) {
if (object->map.size) {
client->driver->unmap(client, object->map.ptr,
object->map.size);
object->map.ptr = NULL;
object->map.size = 0;
}
nvif_object_ioctl(object, &args, sizeof(args), NULL);
object->map.size = 0;
object->map.ptr = NULL;
nvif_object_unmap_handle(object);
}
}
int
nvif_object_map(struct nvif_object *object)
nvif_object_map(struct nvif_object *object, void *argv, u32 argc)
{
struct nvif_client *client = object->client;
struct {
struct nvif_ioctl_v0 ioctl;
struct nvif_ioctl_map_v0 map;
} args = {
.ioctl.type = NVIF_IOCTL_V0_MAP,
};
int ret = nvif_object_ioctl(object, &args, sizeof(args), NULL);
if (ret == 0) {
object->map.size = args.map.length;
object->map.ptr = client->driver->map(client, args.map.handle,
object->map.size);
if (ret = -ENOMEM, object->map.ptr)
u64 handle, length;
int ret = nvif_object_map_handle(object, argv, argc, &handle, &length);
if (ret >= 0) {
if (ret) {
object->map.ptr = client->driver->map(client,
handle,
length);
if (ret = -ENOMEM, object->map.ptr) {
object->map.size = length;
return 0;
}
} else {
object->map.ptr = (void *)(unsigned long)handle;
return 0;
nvif_object_unmap(object);
}
nvif_object_unmap_handle(object);
}
return ret;
}