37 #include <linux/module.h>
39 #include <linux/device.h>
42 #include <linux/poll.h>
43 #include <linux/sched.h>
47 #include <linux/slab.h>
49 #include <asm/uaccess.h>
63 #define IB_UVERBS_BASE_DEV MKDEV(IB_UVERBS_MAJOR, IB_UVERBS_BASE_MINOR)
65 static struct class *uverbs_class;
120 static void ib_uverbs_release_dev(
struct kref *
ref)
128 static void ib_uverbs_release_event_file(
struct kref *
ref)
143 spin_lock_irq(&ev_file->
lock);
148 spin_unlock_irq(&ev_file->
lock);
150 kref_put(&ev_file->
ref, ib_uverbs_release_event_file);
174 static void ib_uverbs_detach_umcast(
struct ib_qp *qp,
186 static int ib_uverbs_cleanup_ucontext(
struct ib_uverbs_file *file,
213 ib_uverbs_detach_umcast(qp, uqp);
273 return context->
device->dealloc_ucontext(context);
276 static void ib_uverbs_release_file(
struct kref *ref)
281 module_put(file->
device->ib_dev->owner);
282 kref_put(&file->
device->ref, ib_uverbs_release_dev);
287 static ssize_t ib_uverbs_event_read(
struct file *filp,
char __user *
buf,
295 spin_lock_irq(&file->
lock);
298 spin_unlock_irq(&file->
lock);
307 spin_lock_irq(&file->
lock);
317 if (eventsz > count) {
328 spin_unlock_irq(&file->
lock);
342 static unsigned int ib_uverbs_event_poll(
struct file *filp,
345 unsigned int pollflags = 0;
350 spin_lock_irq(&file->
lock);
353 spin_unlock_irq(&file->
lock);
358 static int ib_uverbs_event_fasync(
int fd,
struct file *filp,
int on)
365 static int ib_uverbs_event_close(
struct inode *
inode,
struct file *filp)
370 spin_lock_irq(&file->
lock);
377 spin_unlock_irq(&file->
lock);
381 kref_put(&file->
uverbs_file->ref, ib_uverbs_release_file);
383 kref_put(&file->
ref, ib_uverbs_release_event_file);
390 .read = ib_uverbs_event_read,
391 .poll = ib_uverbs_event_poll,
392 .release = ib_uverbs_event_close,
393 .fasync = ib_uverbs_event_fasync,
409 spin_unlock_irqrestore(&file->
lock, flags);
415 spin_unlock_irqrestore(&file->
lock, flags);
426 spin_unlock_irqrestore(&file->
lock, flags);
442 spin_unlock_irqrestore(&file->
async_file->lock, flags);
448 spin_unlock_irqrestore(&file->
async_file->lock, flags);
459 spin_unlock_irqrestore(&file->
async_file->lock, flags);
482 ib_uverbs_async_handler(context_ptr, uobj->
uobject.user_handle,
494 ib_uverbs_async_handler(context_ptr, uobj->
uobject.user_handle,
519 kref_init(&ev_file->
ref);
544 struct fd f = fdget(fd);
549 if (f.
file->f_op != &uverbs_event_fops)
552 ev_file = f.
file->private_data;
558 kref_get(&ev_file->
ref);
565 static ssize_t ib_uverbs_write(
struct file *filp,
const char __user *buf,
566 size_t count, loff_t *pos)
571 if (count <
sizeof hdr)
577 if (
hdr.in_words * 4 != count)
581 !uverbs_cmd_table[
hdr.command])
588 if (!(file->
device->ib_dev->uverbs_cmd_mask & (1ull <<
hdr.command)))
591 return uverbs_cmd_table[
hdr.command](
file, buf +
sizeof hdr,
592 hdr.in_words * 4, hdr.out_words * 4);
595 static int ib_uverbs_mmap(
struct file *filp,
struct vm_area_struct *vma)
615 static int ib_uverbs_open(
struct inode *inode,
struct file *filp)
627 if (!try_module_get(dev->
ib_dev->owner)) {
641 kref_init(&file->
ref);
649 module_put(dev->
ib_dev->owner);
652 kref_put(&dev->
ref, ib_uverbs_release_dev);
656 static int ib_uverbs_close(
struct inode *inode,
struct file *filp)
660 ib_uverbs_cleanup_ucontext(file, file->
ucontext);
663 kref_put(&file->
async_file->ref, ib_uverbs_release_event_file);
665 kref_put(&file->
ref, ib_uverbs_release_file);
672 .write = ib_uverbs_write,
673 .open = ib_uverbs_open,
674 .release = ib_uverbs_close,
680 .write = ib_uverbs_write,
681 .mmap = ib_uverbs_mmap,
682 .open = ib_uverbs_open,
683 .release = ib_uverbs_close,
687 static struct ib_client uverbs_client = {
689 .add = ib_uverbs_add_one,
690 .remove = ib_uverbs_remove_one
705 static ssize_t show_dev_abi_version(
struct device *device,
720 static dev_t overflow_maj;
728 static int find_overflow_devnum(
void)
736 printk(
KERN_ERR "user_verbs: couldn't register dynamic device number\n");
748 static void ib_uverbs_add_one(
struct ib_device *device)
757 uverbs_dev = kzalloc(
sizeof *uverbs_dev,
GFP_KERNEL);
761 kref_init(&uverbs_dev->
ref);
762 init_completion(&uverbs_dev->
comp);
766 spin_lock(&map_lock);
769 spin_unlock(&map_lock);
770 devnum = find_overflow_devnum();
774 spin_lock(&map_lock);
776 base = devnum + overflow_maj;
783 spin_unlock(&map_lock);
785 uverbs_dev->
ib_dev = device;
790 uverbs_dev->
cdev.ops = device->
mmap ? &uverbs_mmap_fops : &uverbs_fops;
796 uverbs_dev->
cdev.dev, uverbs_dev,
797 "uverbs%d", uverbs_dev->
devnum);
798 if (IS_ERR(uverbs_dev->
dev))
821 kref_put(&uverbs_dev->
ref, ib_uverbs_release_dev);
827 static void ib_uverbs_remove_one(
struct ib_device *device)
843 kref_put(&uverbs_dev->
ref, ib_uverbs_release_dev);
848 static char *uverbs_devnode(
struct device *dev,
umode_t *
mode)
855 static int __init ib_uverbs_init(
void)
867 if (IS_ERR(uverbs_class)) {
868 ret = PTR_ERR(uverbs_class);
869 printk(
KERN_ERR "user_verbs: couldn't create class infiniband_verbs\n");
873 uverbs_class->
devnode = uverbs_devnode;
877 printk(
KERN_ERR "user_verbs: couldn't create abi_version attribute\n");
899 static void __exit ib_uverbs_cleanup(
void)