diff --git a/drivers/gpu/nvgpu/Makefile.nvgpu b/drivers/gpu/nvgpu/Makefile.nvgpu index 9186bcc73..e9e7581a5 100644 --- a/drivers/gpu/nvgpu/Makefile.nvgpu +++ b/drivers/gpu/nvgpu/Makefile.nvgpu @@ -27,6 +27,7 @@ nvgpu-y := \ common/linux/timers.o \ common/linux/ioctl.o \ common/linux/ioctl_ctrl.o \ + common/linux/ioctl_as.o \ common/mm/nvgpu_allocator.o \ common/mm/bitmap_allocator.o \ common/mm/buddy_allocator.o \ @@ -35,12 +36,12 @@ nvgpu-y := \ common/pramin.o \ common/nvgpu_common.o \ common/semaphore.o \ + common/as.o \ common/vbios/bios.o \ gk20a/gk20a.o \ gk20a/bus_gk20a.o \ gk20a/pramin_gk20a.o \ gk20a/sched_gk20a.o \ - gk20a/as_gk20a.o \ gk20a/ce2_gk20a.o \ gk20a/fifo_gk20a.o \ gk20a/channel_gk20a.o \ diff --git a/drivers/gpu/nvgpu/common/as.c b/drivers/gpu/nvgpu/common/as.c new file mode 100644 index 000000000..3182642aa --- /dev/null +++ b/drivers/gpu/nvgpu/common/as.c @@ -0,0 +1,99 @@ +/* + * GK20A Address Spaces + * + * Copyright (c) 2011-2017, NVIDIA CORPORATION. All rights reserved. + * + * This program is free software; you can redistribute it and/or modify it + * under the terms and conditions of the GNU General Public License, + * version 2, as published by the Free Software Foundation. + * + * This program is distributed in the hope it will be useful, but WITHOUT + * ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or + * FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for + * more details. + */ + +#include + +#include + +#include "gk20a/gk20a.h" + +/* dumb allocator... */ +static int generate_as_share_id(struct gk20a_as *as) +{ + gk20a_dbg_fn(""); + return ++as->last_share_id; +} +/* still dumb */ +static void release_as_share_id(struct gk20a_as *as, int id) +{ + gk20a_dbg_fn(""); + return; +} + +int gk20a_as_alloc_share(struct gk20a *g, + u32 big_page_size, u32 flags, + struct gk20a_as_share **out) +{ + struct gk20a_as_share *as_share; + int err = 0; + + gk20a_dbg_fn(""); + g = gk20a_get(g); + if (!g) + return -ENODEV; + + *out = NULL; + as_share = nvgpu_kzalloc(g, sizeof(*as_share)); + if (!as_share) + return -ENOMEM; + + as_share->as = &g->as; + as_share->id = generate_as_share_id(as_share->as); + + /* this will set as_share->vm. */ + err = gk20a_busy(g); + if (err) + goto failed; + err = g->ops.mm.vm_alloc_share(as_share, big_page_size, flags); + gk20a_idle(g); + + if (err) + goto failed; + + *out = as_share; + return 0; + +failed: + nvgpu_kfree(g, as_share); + return err; +} + +/* + * channels and the device nodes call this to release. + * once the ref_cnt hits zero the share is deleted. + */ +int gk20a_as_release_share(struct gk20a_as_share *as_share) +{ + struct gk20a *g = as_share->vm->mm->g; + int err; + + gk20a_dbg_fn(""); + + err = gk20a_busy(g); + + if (err) + goto release_fail; + + err = gk20a_vm_release_share(as_share); + + gk20a_idle(g); + +release_fail: + release_as_share_id(as_share->as, as_share->id); + gk20a_put(g); + nvgpu_kfree(g, as_share); + + return err; +} diff --git a/drivers/gpu/nvgpu/common/linux/ioctl.c b/drivers/gpu/nvgpu/common/linux/ioctl.c index 202ea0efb..53b9476e6 100644 --- a/drivers/gpu/nvgpu/common/linux/ioctl.c +++ b/drivers/gpu/nvgpu/common/linux/ioctl.c @@ -24,9 +24,9 @@ #include "gk20a/dbg_gpu_gk20a.h" #include "gk20a/ctxsw_trace_gk20a.h" #include "gk20a/channel_gk20a.h" -#include "gk20a/as_gk20a.h" #include "gk20a/tsg_gk20a.h" #include "ioctl_ctrl.h" +#include "ioctl_as.h" #define GK20A_NUM_CDEVS 7 @@ -167,9 +167,9 @@ void gk20a_user_deinit(struct device *dev, struct class *class) cdev_del(&g->channel.cdev); } - if (g->as.node) { - device_destroy(class, g->as.cdev.dev); - cdev_del(&g->as.cdev); + if (g->as_dev.node) { + device_destroy(class, g->as_dev.cdev.dev); + cdev_del(&g->as_dev.cdev); } if (g->ctrl.node) { @@ -228,7 +228,7 @@ int gk20a_user_init(struct device *dev, const char *interface_name, goto fail; err = gk20a_create_device(dev, devno++, interface_name, "-as", - &g->as.cdev, &g->as.node, + &g->as_dev.cdev, &g->as_dev.node, &gk20a_as_ops, class); if (err) diff --git a/drivers/gpu/nvgpu/gk20a/as_gk20a.c b/drivers/gpu/nvgpu/common/linux/ioctl_as.c similarity index 85% rename from drivers/gpu/nvgpu/gk20a/as_gk20a.c rename to drivers/gpu/nvgpu/common/linux/ioctl_as.c index 5acc626bc..ff9787dbd 100644 --- a/drivers/gpu/nvgpu/gk20a/as_gk20a.c +++ b/drivers/gpu/nvgpu/common/linux/ioctl_as.c @@ -13,8 +13,6 @@ * more details. */ -#include -#include #include #include @@ -22,89 +20,7 @@ #include -#include - -#include "gk20a.h" - -/* dumb allocator... */ -static int generate_as_share_id(struct gk20a_as *as) -{ - gk20a_dbg_fn(""); - return ++as->last_share_id; -} -/* still dumb */ -static void release_as_share_id(struct gk20a_as *as, int id) -{ - gk20a_dbg_fn(""); - return; -} - -int gk20a_as_alloc_share(struct gk20a_as *as, - u32 big_page_size, u32 flags, - struct gk20a_as_share **out) -{ - struct gk20a *g = gk20a_from_as(as); - struct gk20a_as_share *as_share; - int err = 0; - - gk20a_dbg_fn(""); - g = gk20a_get(g); - if (!g) - return -ENODEV; - - *out = NULL; - as_share = nvgpu_kzalloc(g, sizeof(*as_share)); - if (!as_share) - return -ENOMEM; - - as_share->as = as; - as_share->id = generate_as_share_id(as_share->as); - - /* this will set as_share->vm. */ - err = gk20a_busy(g); - if (err) - goto failed; - err = g->ops.mm.vm_alloc_share(as_share, big_page_size, flags); - gk20a_idle(g); - - if (err) - goto failed; - - *out = as_share; - return 0; - -failed: - nvgpu_kfree(g, as_share); - return err; -} - -/* - * channels and the device nodes call this to release. - * once the ref_cnt hits zero the share is deleted. - */ -int gk20a_as_release_share(struct gk20a_as_share *as_share) -{ - struct gk20a *g = as_share->vm->mm->g; - int err; - - gk20a_dbg_fn(""); - - err = gk20a_busy(g); - - if (err) - goto release_fail; - - err = gk20a_vm_release_share(as_share); - - gk20a_idle(g); - -release_fail: - release_as_share_id(as_share->as, as_share->id); - nvgpu_kfree(g, as_share); - gk20a_put(g); - - return err; -} +#include "gk20a/gk20a.h" static int gk20a_as_ioctl_bind_channel( struct gk20a_as_share *as_share, @@ -333,9 +249,9 @@ int gk20a_as_dev_open(struct inode *inode, struct file *filp) gk20a_dbg_fn(""); - g = container_of(inode->i_cdev, struct gk20a, as.cdev); + g = container_of(inode->i_cdev, struct gk20a, as_dev.cdev); - err = gk20a_as_alloc_share(&g->as, 0, 0, &as_share); + err = gk20a_as_alloc_share(g, 0, 0, &as_share); if (err) { gk20a_dbg_fn("failed to alloc share"); return err; diff --git a/drivers/gpu/nvgpu/common/linux/ioctl_as.h b/drivers/gpu/nvgpu/common/linux/ioctl_as.h new file mode 100644 index 000000000..ae6690a16 --- /dev/null +++ b/drivers/gpu/nvgpu/common/linux/ioctl_as.h @@ -0,0 +1,26 @@ +/* + * GK20A Address Spaces + * + * Copyright (c) 2011-2017, NVIDIA CORPORATION. All rights reserved. + * + * This program is free software; you can redistribute it and/or modify it + * under the terms and conditions of the GNU General Public License, + * version 2, as published by the Free Software Foundation. + * + * This program is distributed in the hope it will be useful, but WITHOUT + * ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or + * FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for + * more details. + */ +#ifndef __NVGPU_COMMON_LINUX_AS_H__ +#define __NVGPU_COMMON_LINUX_AS_H__ + +struct inode; +struct file; + +/* struct file_operations driver interface */ +int gk20a_as_dev_open(struct inode *inode, struct file *filp); +int gk20a_as_dev_release(struct inode *inode, struct file *filp); +long gk20a_as_dev_ioctl(struct file *filp, unsigned int cmd, unsigned long arg); + +#endif diff --git a/drivers/gpu/nvgpu/common/linux/ioctl_ctrl.c b/drivers/gpu/nvgpu/common/linux/ioctl_ctrl.c index fa05deb92..6aa376ea7 100644 --- a/drivers/gpu/nvgpu/common/linux/ioctl_ctrl.c +++ b/drivers/gpu/nvgpu/common/linux/ioctl_ctrl.c @@ -205,13 +205,13 @@ static int gk20a_ctrl_alloc_as( snprintf(name, sizeof(name), "nvhost-%s-fd%d", g->name, fd); - file = anon_inode_getfile(name, g->as.cdev.ops, NULL, O_RDWR); + file = anon_inode_getfile(name, g->as_dev.cdev.ops, NULL, O_RDWR); if (IS_ERR(file)) { err = PTR_ERR(file); goto clean_up; } - err = gk20a_as_alloc_share(&g->as, args->big_page_size, args->flags, + err = gk20a_as_alloc_share(g, args->big_page_size, args->flags, &as_share); if (err) goto clean_up_file; diff --git a/drivers/gpu/nvgpu/gk20a/gk20a.h b/drivers/gpu/nvgpu/gk20a/gk20a.h index 451e32ca8..1158add1a 100644 --- a/drivers/gpu/nvgpu/gk20a/gk20a.h +++ b/drivers/gpu/nvgpu/gk20a/gk20a.h @@ -37,13 +37,14 @@ struct dbg_profiler_object_data; #include #include #include +#include #include "../../../arch/arm/mach-tegra/iomap.h" #include #include +#include -#include "as_gk20a.h" #include "clk_gk20a.h" #include "ce2_gk20a.h" #include "fifo_gk20a.h" @@ -1041,6 +1042,11 @@ struct gk20a { struct device *node; } ctrl; + struct { + struct cdev cdev; + struct device *node; + } as_dev; + struct { struct cdev cdev; struct device *node; diff --git a/drivers/gpu/nvgpu/gk20a/as_gk20a.h b/drivers/gpu/nvgpu/include/nvgpu/as.h similarity index 59% rename from drivers/gpu/nvgpu/gk20a/as_gk20a.h rename to drivers/gpu/nvgpu/include/nvgpu/as.h index 9b0c6e142..0e784396d 100644 --- a/drivers/gpu/nvgpu/gk20a/as_gk20a.h +++ b/drivers/gpu/nvgpu/include/nvgpu/as.h @@ -1,7 +1,7 @@ /* * GK20A Address Spaces * - * Copyright (c) 2011-2015, NVIDIA CORPORATION. All rights reserved. + * Copyright (c) 2011-2017, NVIDIA CORPORATION. All rights reserved. * * This program is free software; you can redistribute it and/or modify it * under the terms and conditions of the GNU General Public License, @@ -12,15 +12,9 @@ * FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for * more details. */ -#ifndef AS_GK20A_H -#define AS_GK20A_H +#ifndef __NVGPU_AS_H__ +#define __NVGPU_AS_H__ -#include -#include -#include - -struct gk20a_as; -struct gk20a_as_share; struct vm_gk20a; struct gk20a_as_share { @@ -31,19 +25,12 @@ struct gk20a_as_share { struct gk20a_as { int last_share_id; /* dummy allocator for now */ - struct cdev cdev; - struct device *node; }; int gk20a_as_release_share(struct gk20a_as_share *as_share); -/* struct file_operations driver interface */ -int gk20a_as_dev_open(struct inode *inode, struct file *filp); -int gk20a_as_dev_release(struct inode *inode, struct file *filp); -long gk20a_as_dev_ioctl(struct file *filp, unsigned int cmd, unsigned long arg); - /* if big_page_size == 0, the default big page size is used */ -int gk20a_as_alloc_share(struct gk20a_as *as, u32 big_page_size, +int gk20a_as_alloc_share(struct gk20a *g, u32 big_page_size, u32 flags, struct gk20a_as_share **out); #endif