X-Git-Url: http://git.lttng.org./?a=blobdiff_plain;f=ltt-debugfs-abi.c;h=fe5f5b1b354310ea0c083cb53c3504aae7c875c9;hb=refs%2Ftags%2Fv2.0-pre1;hp=0aa2cec03381ea0f58d121f1136cc6e7544b9455;hpb=96ba7208aa8009345a525148e32f78cd8d4693ab;p=lttng-modules.git diff --git a/ltt-debugfs-abi.c b/ltt-debugfs-abi.c index 0aa2cec0..fe5f5b1b 100644 --- a/ltt-debugfs-abi.c +++ b/ltt-debugfs-abi.c @@ -49,6 +49,11 @@ static const struct file_operations lttng_channel_fops; static const struct file_operations lttng_metadata_fops; static const struct file_operations lttng_event_fops; +/* + * Teardown management: opened file descriptors keep a refcount on the module, + * so it can only exit when all file descriptors are closed. + */ + enum channel_type { PER_CPU_CHANNEL, METADATA_CHANNEL, @@ -221,6 +226,7 @@ long lttng_ioctl(struct file *file, unsigned int cmd, unsigned long arg) } static const struct file_operations lttng_fops = { + .owner = THIS_MODULE, .unlocked_ioctl = lttng_ioctl, #ifdef CONFIG_COMPAT .compat_ioctl = lttng_ioctl, @@ -241,7 +247,6 @@ void lttng_metadata_create_events(struct file *channel_file) .name = "lttng_metadata", }; struct ltt_event *event; - int ret; /* * We tolerate no failure path after event creation. It will stay @@ -249,7 +254,6 @@ void lttng_metadata_create_events(struct file *channel_file) */ event = ltt_event_create(channel, &metadata_params, NULL); if (!event) { - ret = -EINVAL; goto create_error; } return; @@ -265,7 +269,7 @@ int lttng_abi_create_channel(struct file *session_file, enum channel_type channel_type) { struct ltt_session *session = session_file->private_data; - const struct file_operations *fops; + const struct file_operations *fops = NULL; const char *transport_name; struct ltt_channel *chan; struct file *chan_file; @@ -280,8 +284,17 @@ int lttng_abi_create_channel(struct file *session_file, ret = chan_fd; goto fd_error; } + switch (channel_type) { + case PER_CPU_CHANNEL: + fops = <tng_channel_fops; + break; + case METADATA_CHANNEL: + fops = <tng_metadata_fops; + break; + } + chan_file = anon_inode_getfile("[lttng_channel]", - <tng_channel_fops, + fops, NULL, O_RDWR); if (IS_ERR(chan_file)) { ret = PTR_ERR(chan_file); @@ -298,7 +311,6 @@ int lttng_abi_create_channel(struct file *session_file, } else { return -EINVAL; } - fops = <tng_channel_fops; break; case METADATA_CHANNEL: if (chan_param.output == LTTNG_KERNEL_SPLICE) @@ -307,7 +319,6 @@ int lttng_abi_create_channel(struct file *session_file, transport_name = "relay-metadata-mmap"; else return -EINVAL; - fops = <tng_metadata_fops; break; default: transport_name = ""; @@ -410,6 +421,7 @@ int lttng_session_release(struct inode *inode, struct file *file) } static const struct file_operations lttng_session_fops = { + .owner = THIS_MODULE, .release = lttng_session_release, .unlocked_ioctl = lttng_session_ioctl, #ifdef CONFIG_COMPAT @@ -609,8 +621,9 @@ unsigned int lttng_channel_poll(struct file *file, poll_table *wait) return POLLERR; if (channel->ops->is_finalized(channel->chan)) return POLLHUP; - else + if (channel->ops->buffer_has_read_closed_stream(channel->chan)) return POLLIN | POLLRDNORM; + return 0; } return mask; @@ -627,6 +640,7 @@ int lttng_channel_release(struct inode *inode, struct file *file) } static const struct file_operations lttng_channel_fops = { + .owner = THIS_MODULE, .release = lttng_channel_release, .poll = lttng_channel_poll, .unlocked_ioctl = lttng_channel_ioctl, @@ -636,6 +650,7 @@ static const struct file_operations lttng_channel_fops = { }; static const struct file_operations lttng_metadata_fops = { + .owner = THIS_MODULE, .release = lttng_channel_release, .unlocked_ioctl = lttng_metadata_ioctl, #ifdef CONFIG_COMPAT @@ -689,6 +704,7 @@ int lttng_event_release(struct inode *inode, struct file *file) /* TODO: filter control ioctl */ static const struct file_operations lttng_event_fops = { + .owner = THIS_MODULE, .release = lttng_event_release, .unlocked_ioctl = lttng_event_ioctl, #ifdef CONFIG_COMPAT