X-Git-Url: http://git.liburcu.org/?p=lttng-modules.git;a=blobdiff_plain;f=lttng-abi.c;h=1b5239e51164112932c87bbc47637db9d54d23d3;hp=c535cb95d4814a0f0e50debc496dbec66b767ff3;hb=2459130397d7e7eecc44a5f06a39d65c78257eef;hpb=9f36eaed6f91d5897924b551b44d1edd8cee00e2 diff --git a/lttng-abi.c b/lttng-abi.c index c535cb95..1b5239e5 100644 --- a/lttng-abi.c +++ b/lttng-abi.c @@ -1,4 +1,4 @@ -/* SPDX-License-Identifier: (GPL-2.0 or LGPL-2.1) +/* SPDX-License-Identifier: (GPL-2.0-only or LGPL-2.1-only) * * lttng-abi.c * @@ -30,10 +30,10 @@ #include #include #include -#include /* for wrapper_vmalloc_sync_all() */ -#include -#include -#include +#include /* for wrapper_vmalloc_sync_mappings() */ +#include +#include +#include #include #include #include @@ -43,7 +43,7 @@ #include #include #include -#include +#include /* * This is LTTng's own personal way to create a system call as an external @@ -51,7 +51,13 @@ */ static struct proc_dir_entry *lttng_proc_dentry; -static const struct file_operations lttng_fops; + +#if (LINUX_VERSION_CODE >= KERNEL_VERSION(5,6,0)) +static const struct proc_ops lttng_proc_ops; +#else +static const struct file_operations lttng_proc_ops; +#endif + static const struct file_operations lttng_session_fops; static const struct file_operations lttng_channel_fops; static const struct file_operations lttng_metadata_fops; @@ -236,6 +242,44 @@ long lttng_abi_add_context(struct file *file, case LTTNG_KERNEL_CONTEXT_CALLSTACK_KERNEL: case LTTNG_KERNEL_CONTEXT_CALLSTACK_USER: return lttng_add_callstack_to_ctx(ctx, context_param->ctx); + case LTTNG_KERNEL_CONTEXT_CGROUP_NS: + return lttng_add_cgroup_ns_to_ctx(ctx); + case LTTNG_KERNEL_CONTEXT_IPC_NS: + return lttng_add_ipc_ns_to_ctx(ctx); + case LTTNG_KERNEL_CONTEXT_MNT_NS: + return lttng_add_mnt_ns_to_ctx(ctx); + case LTTNG_KERNEL_CONTEXT_NET_NS: + return lttng_add_net_ns_to_ctx(ctx); + case LTTNG_KERNEL_CONTEXT_PID_NS: + return lttng_add_pid_ns_to_ctx(ctx); + case LTTNG_KERNEL_CONTEXT_USER_NS: + return lttng_add_user_ns_to_ctx(ctx); + case LTTNG_KERNEL_CONTEXT_UTS_NS: + return lttng_add_uts_ns_to_ctx(ctx); + case LTTNG_KERNEL_CONTEXT_UID: + return lttng_add_uid_to_ctx(ctx); + case LTTNG_KERNEL_CONTEXT_EUID: + return lttng_add_euid_to_ctx(ctx); + case LTTNG_KERNEL_CONTEXT_SUID: + return lttng_add_suid_to_ctx(ctx); + case LTTNG_KERNEL_CONTEXT_GID: + return lttng_add_gid_to_ctx(ctx); + case LTTNG_KERNEL_CONTEXT_EGID: + return lttng_add_egid_to_ctx(ctx); + case LTTNG_KERNEL_CONTEXT_SGID: + return lttng_add_sgid_to_ctx(ctx); + case LTTNG_KERNEL_CONTEXT_VUID: + return lttng_add_vuid_to_ctx(ctx); + case LTTNG_KERNEL_CONTEXT_VEUID: + return lttng_add_veuid_to_ctx(ctx); + case LTTNG_KERNEL_CONTEXT_VSUID: + return lttng_add_vsuid_to_ctx(ctx); + case LTTNG_KERNEL_CONTEXT_VGID: + return lttng_add_vgid_to_ctx(ctx); + case LTTNG_KERNEL_CONTEXT_VEGID: + return lttng_add_vegid_to_ctx(ctx); + case LTTNG_KERNEL_CONTEXT_VSGID: + return lttng_add_vsgid_to_ctx(ctx); default: return -EINVAL; } @@ -353,13 +397,22 @@ long lttng_ioctl(struct file *file, unsigned int cmd, unsigned long arg) } } -static const struct file_operations lttng_fops = { +#if (LINUX_VERSION_CODE >= KERNEL_VERSION(5,6,0)) +static const struct proc_ops lttng_proc_ops = { + .proc_ioctl = lttng_ioctl, +#ifdef CONFIG_COMPAT + .proc_compat_ioctl = lttng_ioctl, +#endif /* CONFIG_COMPAT */ +}; +#else +static const struct file_operations lttng_proc_ops = { .owner = THIS_MODULE, .unlocked_ioctl = lttng_ioctl, #ifdef CONFIG_COMPAT .compat_ioctl = lttng_ioctl, -#endif +#endif /* CONFIG_COMPAT */ }; +#endif static int lttng_abi_create_channel(struct file *session_file, @@ -419,8 +472,8 @@ int lttng_abi_create_channel(struct file *session_file, transport_name = ""; break; } - if (atomic_long_add_unless(&session_file->f_count, - 1, INT_MAX) == INT_MAX) { + if (!atomic_long_add_unless(&session_file->f_count, 1, LONG_MAX)) { + ret = -EOVERFLOW; goto refcount_error; } /* @@ -453,6 +506,61 @@ fd_error: return ret; } +static +int lttng_abi_session_set_name(struct lttng_session *session, + struct lttng_kernel_session_name *name) +{ + size_t len; + + len = strnlen(name->name, LTTNG_KERNEL_SESSION_NAME_LEN); + + if (len == LTTNG_KERNEL_SESSION_NAME_LEN) { + /* Name is too long/malformed */ + return -EINVAL; + } + + strcpy(session->name, name->name); + return 0; +} + +static +int lttng_abi_session_set_creation_time(struct lttng_session *session, + struct lttng_kernel_session_creation_time *time) +{ + size_t len; + + len = strnlen(time->iso8601, LTTNG_KERNEL_SESSION_CREATION_TIME_ISO8601_LEN); + + if (len == LTTNG_KERNEL_SESSION_CREATION_TIME_ISO8601_LEN) { + /* Time is too long/malformed */ + return -EINVAL; + } + + strcpy(session->creation_time, time->iso8601); + return 0; +} + +static +enum tracker_type get_tracker_type(struct lttng_kernel_tracker_args *tracker) +{ + switch (tracker->type) { + case LTTNG_KERNEL_TRACKER_PID: + return TRACKER_PID; + case LTTNG_KERNEL_TRACKER_VPID: + return TRACKER_VPID; + case LTTNG_KERNEL_TRACKER_UID: + return TRACKER_UID; + case LTTNG_KERNEL_TRACKER_VUID: + return TRACKER_VUID; + case LTTNG_KERNEL_TRACKER_GID: + return TRACKER_GID; + case LTTNG_KERNEL_TRACKER_VGID: + return TRACKER_VGID; + default: + return TRACKER_UNKNOWN; + } +} + /** * lttng_session_ioctl - lttng session fd ioctl * @@ -470,9 +578,13 @@ fd_error: * LTTNG_KERNEL_METADATA * Returns a LTTng metadata file descriptor * LTTNG_KERNEL_SESSION_TRACK_PID - * Add PID to session tracker + * Add PID to session PID tracker * LTTNG_KERNEL_SESSION_UNTRACK_PID - * Remove PID from session tracker + * Remove PID from session PID tracker + * LTTNG_KERNEL_SESSION_TRACK_ID + * Add ID to tracker + * LTTNG_KERNEL_SESSION_UNTRACK_ID + * Remove ID from tracker * * The returned channel will be deleted when its file descriptor is closed. */ @@ -480,13 +592,12 @@ static long lttng_session_ioctl(struct file *file, unsigned int cmd, unsigned long arg) { struct lttng_session *session = file->private_data; + struct lttng_kernel_channel chan_param; + struct lttng_kernel_old_channel old_chan_param; switch (cmd) { case LTTNG_KERNEL_OLD_CHANNEL: { - struct lttng_kernel_channel chan_param; - struct lttng_kernel_old_channel old_chan_param; - if (copy_from_user(&old_chan_param, (struct lttng_kernel_old_channel __user *) arg, sizeof(struct lttng_kernel_old_channel))) @@ -503,8 +614,6 @@ long lttng_session_ioctl(struct file *file, unsigned int cmd, unsigned long arg) } case LTTNG_KERNEL_CHANNEL: { - struct lttng_kernel_channel chan_param; - if (copy_from_user(&chan_param, (struct lttng_kernel_channel __user *) arg, sizeof(struct lttng_kernel_channel))) @@ -524,9 +633,6 @@ long lttng_session_ioctl(struct file *file, unsigned int cmd, unsigned long arg) return lttng_session_disable(session); case LTTNG_KERNEL_OLD_METADATA: { - struct lttng_kernel_channel chan_param; - struct lttng_kernel_old_channel old_chan_param; - if (copy_from_user(&old_chan_param, (struct lttng_kernel_old_channel __user *) arg, sizeof(struct lttng_kernel_old_channel))) @@ -543,8 +649,6 @@ long lttng_session_ioctl(struct file *file, unsigned int cmd, unsigned long arg) } case LTTNG_KERNEL_METADATA: { - struct lttng_kernel_channel chan_param; - if (copy_from_user(&chan_param, (struct lttng_kernel_channel __user *) arg, sizeof(struct lttng_kernel_channel))) @@ -553,15 +657,78 @@ long lttng_session_ioctl(struct file *file, unsigned int cmd, unsigned long arg) METADATA_CHANNEL); } case LTTNG_KERNEL_SESSION_TRACK_PID: - return lttng_session_track_pid(session, (int) arg); + return lttng_session_track_id(session, TRACKER_PID, (int) arg); case LTTNG_KERNEL_SESSION_UNTRACK_PID: - return lttng_session_untrack_pid(session, (int) arg); + return lttng_session_untrack_id(session, TRACKER_PID, (int) arg); + case LTTNG_KERNEL_SESSION_TRACK_ID: + { + struct lttng_kernel_tracker_args tracker; + enum tracker_type tracker_type; + + if (copy_from_user(&tracker, + (struct lttng_kernel_tracker_args __user *) arg, + sizeof(struct lttng_kernel_tracker_args))) + return -EFAULT; + tracker_type = get_tracker_type(&tracker); + if (tracker_type == TRACKER_UNKNOWN) + return -EINVAL; + return lttng_session_track_id(session, tracker_type, tracker.id); + } + case LTTNG_KERNEL_SESSION_UNTRACK_ID: + { + struct lttng_kernel_tracker_args tracker; + enum tracker_type tracker_type; + + if (copy_from_user(&tracker, + (struct lttng_kernel_tracker_args __user *) arg, + sizeof(struct lttng_kernel_tracker_args))) + return -EFAULT; + tracker_type = get_tracker_type(&tracker); + if (tracker_type == TRACKER_UNKNOWN) + return -EINVAL; + return lttng_session_untrack_id(session, tracker_type, + tracker.id); + } case LTTNG_KERNEL_SESSION_LIST_TRACKER_PIDS: - return lttng_session_list_tracker_pids(session); + return lttng_session_list_tracker_ids(session, TRACKER_PID); + case LTTNG_KERNEL_SESSION_LIST_TRACKER_IDS: + { + struct lttng_kernel_tracker_args tracker; + enum tracker_type tracker_type; + + if (copy_from_user(&tracker, + (struct lttng_kernel_tracker_args __user *) arg, + sizeof(struct lttng_kernel_tracker_args))) + return -EFAULT; + tracker_type = get_tracker_type(&tracker); + if (tracker_type == TRACKER_UNKNOWN) + return -EINVAL; + return lttng_session_list_tracker_ids(session, tracker_type); + } case LTTNG_KERNEL_SESSION_METADATA_REGEN: return lttng_session_metadata_regenerate(session); case LTTNG_KERNEL_SESSION_STATEDUMP: return lttng_session_statedump(session); + case LTTNG_KERNEL_SESSION_SET_NAME: + { + struct lttng_kernel_session_name name; + + if (copy_from_user(&name, + (struct lttng_kernel_session_name __user *) arg, + sizeof(struct lttng_kernel_session_name))) + return -EFAULT; + return lttng_abi_session_set_name(session, &name); + } + case LTTNG_KERNEL_SESSION_SET_CREATION_TIME: + { + struct lttng_kernel_session_creation_time time; + + if (copy_from_user(&time, + (struct lttng_kernel_session_creation_time __user *) arg, + sizeof(struct lttng_kernel_session_creation_time))) + return -EFAULT; + return lttng_abi_session_set_creation_time(session, &time); + } default: return -ENOIOCTLCMD; } @@ -1054,7 +1221,8 @@ int lttng_abi_create_event(struct file *channel_file, event_param->u.kprobe.symbol_name[LTTNG_KERNEL_SYM_NAME_LEN - 1] = '\0'; break; case LTTNG_KERNEL_FUNCTION: - event_param->u.ftrace.symbol_name[LTTNG_KERNEL_SYM_NAME_LEN - 1] = '\0'; + WARN_ON_ONCE(1); + /* Not implemented. */ break; default: break; @@ -1072,8 +1240,7 @@ int lttng_abi_create_event(struct file *channel_file, goto file_error; } /* The event holds a reference on the channel */ - if (atomic_long_add_unless(&channel_file->f_count, - 1, INT_MAX) == INT_MAX) { + if (!atomic_long_add_unless(&channel_file->f_count, 1, LONG_MAX)) { ret = -EOVERFLOW; goto refcount_error; } @@ -1206,9 +1373,8 @@ long lttng_channel_ioctl(struct file *file, unsigned int cmd, unsigned long arg) sizeof(uevent_param->u.kretprobe.symbol_name)); break; case LTTNG_KERNEL_FUNCTION: - memcpy(uevent_param->u.ftrace.symbol_name, - old_uevent_param->u.ftrace.symbol_name, - sizeof(uevent_param->u.ftrace.symbol_name)); + WARN_ON_ONCE(1); + /* Not implemented. */ break; default: break; @@ -1306,7 +1472,6 @@ old_ctx_end: default: return -ENOIOCTLCMD; } - } /** @@ -1473,7 +1638,21 @@ long lttng_event_ioctl(struct file *file, unsigned int cmd, unsigned long arg) return lttng_enabler_attach_bytecode(enabler, (struct lttng_kernel_filter_bytecode __user *) arg); } - + default: + WARN_ON_ONCE(1); + return -ENOSYS; + } + case LTTNG_KERNEL_ADD_CALLSITE: + switch (*evtype) { + case LTTNG_TYPE_EVENT: + event = file->private_data; + return lttng_event_add_callsite(event, + (struct lttng_kernel_event_callsite __user *) arg); + case LTTNG_TYPE_ENABLER: + return -EINVAL; + default: + WARN_ON_ONCE(1); + return -ENOSYS; } default: return -ENOIOCTLCMD; @@ -1759,7 +1938,7 @@ int __init lttng_abi_init(void) { int ret = 0; - wrapper_vmalloc_sync_all(); + wrapper_vmalloc_sync_mappings(); lttng_clock_ref(); ret = lttng_tp_mempool_init(); @@ -1768,7 +1947,7 @@ int __init lttng_abi_init(void) } lttng_proc_dentry = proc_create_data("lttng", S_IRUSR | S_IWUSR, NULL, - <tng_fops, NULL); + <tng_proc_ops, NULL); if (!lttng_proc_dentry) { printk(KERN_ERR "Error creating LTTng control file\n");