From 793c8232937610ae00bc174b87d7fc324346eaea Mon Sep 17 00:00:00 2001 From: Christian Brauner Date: Sat, 26 Jan 2019 11:23:20 +0100 Subject: binder: fix CONFIG_ANDROID_BINDER_DEVICES Several users have tried to only rely on binderfs to provide binder devices and set CONFIG_ANDROID_BINDER_DEVICES="" empty. This is a great use-case of binderfs and one that was always intended to work. However, this is currently not possible since setting CONFIG_ANDROID_BINDER_DEVICES="" emtpy will simply panic the kernel: kobject: (00000000028c2f79): attempted to be registered with empty name! WARNING: CPU: 7 PID: 1703 at lib/kobject.c:228 kobject_add_internal+0x288/0x2b0 Modules linked in: binder_linux(+) bridge stp llc ipmi_ssif gpio_ich dcdbas coretemp kvm_intel kvm irqbypass serio_raw input_leds lpc_ich i5100_edac mac_hid ipmi_si ipmi_devintf ipmi_msghandler sch_fq_codel ib_i CPU: 7 PID: 1703 Comm: modprobe Not tainted 5.0.0-rc2-brauner-binderfs #263 Hardware name: Dell DCS XS24-SC2 /XS24-SC2 , BIOS S59_3C20 04/07/2011 RIP: 0010:kobject_add_internal+0x288/0x2b0 Code: 12 95 48 c7 c7 78 63 3b 95 e8 77 35 71 ff e9 91 fe ff ff 0f 0b eb a7 0f 0b eb 9a 48 89 de 48 c7 c7 00 63 3b 95 e8 f8 95 6a ff <0f> 0b 41 bc ea ff ff ff e9 6d fe ff ff 41 bc fe ff ff ff e9 62 fe RSP: 0018:ffff973f84237a30 EFLAGS: 00010282 RAX: 0000000000000000 RBX: ffff8b53e2472010 RCX: 0000000000000006 RDX: 0000000000000007 RSI: 0000000000000086 RDI: ffff8b53edbd63a0 RBP: ffff973f84237a60 R08: 0000000000000342 R09: 0000000000000004 R10: ffff973f84237af0 R11: 0000000000000001 R12: 0000000000000000 R13: ffff8b53e9f1a1e0 R14: 00000000e9f1a1e0 R15: 0000000000a00037 FS: 00007fbac36f7540(0000) GS:ffff8b53edbc0000(0000) knlGS:0000000000000000 CS: 0010 DS: 0000 ES: 0000 CR0: 0000000080050033 CR2: 00007fbac364cfa7 CR3: 00000004a6d48000 CR4: 00000000000406e0 Call Trace: kobject_add+0x71/0xd0 ? _cond_resched+0x19/0x40 ? mutex_lock+0x12/0x40 device_add+0x12e/0x6b0 device_create_groups_vargs+0xe4/0xf0 device_create_with_groups+0x3f/0x60 ? _cond_resched+0x19/0x40 misc_register+0x140/0x180 binder_init+0x1ed/0x2d4 [binder_linux] ? trace_event_define_fields_binder_transaction_fd_send+0x8e/0x8e [binder_linux] do_one_initcall+0x4a/0x1c9 ? _cond_resched+0x19/0x40 ? kmem_cache_alloc_trace+0x151/0x1c0 do_init_module+0x5f/0x216 load_module+0x223d/0x2b20 __do_sys_finit_module+0xfc/0x120 ? __do_sys_finit_module+0xfc/0x120 __x64_sys_finit_module+0x1a/0x20 do_syscall_64+0x5a/0x120 entry_SYSCALL_64_after_hwframe+0x44/0xa9 RIP: 0033:0x7fbac3202839 Code: 00 f3 c3 66 2e 0f 1f 84 00 00 00 00 00 0f 1f 40 00 48 89 f8 48 89 f7 48 89 d6 48 89 ca 4d 89 c2 4d 89 c8 4c 8b 4c 24 08 0f 05 <48> 3d 01 f0 ff ff 73 01 c3 48 8b 0d 1f f6 2c 00 f7 d8 64 89 01 48 RSP: 002b:00007ffd1494a908 EFLAGS: 00000246 ORIG_RAX: 0000000000000139 RAX: ffffffffffffffda RBX: 000055b629ebec60 RCX: 00007fbac3202839 RDX: 0000000000000000 RSI: 000055b629c20d2e RDI: 0000000000000003 RBP: 000055b629c20d2e R08: 0000000000000000 R09: 000055b629ec2310 R10: 0000000000000003 R11: 0000000000000246 R12: 0000000000000000 R13: 000055b629ebed70 R14: 0000000000040000 R15: 000055b629ebec60 So check for the empty string since strsep() will otherwise return the emtpy string which will cause kobject_add_internal() to panic when trying to add a kobject with an emtpy name. Fixes: ac4812c5ffbb ("binder: Support multiple /dev instances") Cc: Martijn Coenen Signed-off-by: Christian Brauner Acked-by: Todd Kjos Signed-off-by: Greg Kroah-Hartman --- drivers/android/binder.c | 30 ++++++++++++++++-------------- 1 file changed, 16 insertions(+), 14 deletions(-) (limited to 'drivers/android') diff --git a/drivers/android/binder.c b/drivers/android/binder.c index cdfc87629efb..57cf259de600 100644 --- a/drivers/android/binder.c +++ b/drivers/android/binder.c @@ -5898,21 +5898,23 @@ static int __init binder_init(void) &transaction_log_fops); } - /* - * Copy the module_parameter string, because we don't want to - * tokenize it in-place. - */ - device_names = kstrdup(binder_devices_param, GFP_KERNEL); - if (!device_names) { - ret = -ENOMEM; - goto err_alloc_device_names_failed; - } + if (strcmp(binder_devices_param, "") != 0) { + /* + * Copy the module_parameter string, because we don't want to + * tokenize it in-place. + */ + device_names = kstrdup(binder_devices_param, GFP_KERNEL); + if (!device_names) { + ret = -ENOMEM; + goto err_alloc_device_names_failed; + } - device_tmp = device_names; - while ((device_name = strsep(&device_tmp, ","))) { - ret = init_binder_device(device_name); - if (ret) - goto err_init_binder_device_failed; + device_tmp = device_names; + while ((device_name = strsep(&device_tmp, ","))) { + ret = init_binder_device(device_name); + if (ret) + goto err_init_binder_device_failed; + } } return ret; -- cgit v1.2.3-55-g7522 From da8ddba566ff0a883237dbc8c5dadef1ca769e19 Mon Sep 17 00:00:00 2001 From: Christian Brauner Date: Wed, 23 Jan 2019 12:41:15 +0100 Subject: binderfs: respect limit on binder control creation We currently adhere to the reserved devices limit when creating new binderfs devices in binderfs instances not located in the inital ipc namespace. But it is still possible to rob the host instances of their 4 reserved devices by creating the maximum allowed number of devices in a single binderfs instance located in a non-initial ipc namespace and then mounting 4 separate binderfs instances in non-initial ipc namespaces. That happens because the limit is currently not respected for the creation of the initial binder-control device node. Block this nonsense by performing the same check in binderfs_binder_ctl_create() that we perform in binderfs_binder_device_create(). Fixes: 36bdf3cae09d ("binderfs: reserve devices for initial mount") Signed-off-by: Christian Brauner Signed-off-by: Greg Kroah-Hartman --- drivers/android/binderfs.c | 10 +++++++++- 1 file changed, 9 insertions(+), 1 deletion(-) (limited to 'drivers/android') diff --git a/drivers/android/binderfs.c b/drivers/android/binderfs.c index 6a2185eb66c5..7a550104a722 100644 --- a/drivers/android/binderfs.c +++ b/drivers/android/binderfs.c @@ -395,6 +395,11 @@ static int binderfs_binder_ctl_create(struct super_block *sb) struct inode *inode = NULL; struct dentry *root = sb->s_root; struct binderfs_info *info = sb->s_fs_info; +#if defined(CONFIG_IPC_NS) + bool use_reserve = (info->ipc_ns == &init_ipc_ns); +#else + bool use_reserve = true; +#endif device = kzalloc(sizeof(*device), GFP_KERNEL); if (!device) @@ -413,7 +418,10 @@ static int binderfs_binder_ctl_create(struct super_block *sb) /* Reserve a new minor number for the new device. */ mutex_lock(&binderfs_minors_mutex); - minor = ida_alloc_max(&binderfs_minors, BINDERFS_MAX_MINOR, GFP_KERNEL); + minor = ida_alloc_max(&binderfs_minors, + use_reserve ? BINDERFS_MAX_MINOR : + BINDERFS_MAX_MINOR_CAPPED, + GFP_KERNEL); mutex_unlock(&binderfs_minors_mutex); if (minor < 0) { ret = minor; -- cgit v1.2.3-55-g7522 From 5b9633af298bfd1de650f6774d3fada546543101 Mon Sep 17 00:00:00 2001 From: Christian Brauner Date: Thu, 31 Jan 2019 01:25:02 +0100 Subject: binderfs: remove separate device_initcall() binderfs should not have a separate device_initcall(). When a kernel is compiled with CONFIG_ANDROID_BINDERFS register the filesystem alongside CONFIG_ANDROID_IPC. This use-case is especially sensible when users specify CONFIG_ANDROID_IPC=y, CONFIG_ANDROID_BINDERFS=y and ANDROID_BINDER_DEVICES="". When CONFIG_ANDROID_BINDERFS=n then this always succeeds so there's no regression potential for legacy workloads. Signed-off-by: Christian Brauner Signed-off-by: Greg Kroah-Hartman --- drivers/android/binder.c | 7 ++++++- drivers/android/binder_internal.h | 9 +++++++++ drivers/android/binderfs.c | 4 +--- 3 files changed, 16 insertions(+), 4 deletions(-) (limited to 'drivers/android') diff --git a/drivers/android/binder.c b/drivers/android/binder.c index 57cf259de600..4d2b2ad1ee0e 100644 --- a/drivers/android/binder.c +++ b/drivers/android/binder.c @@ -5854,9 +5854,10 @@ static int __init init_binder_device(const char *name) static int __init binder_init(void) { int ret; - char *device_name, *device_names, *device_tmp; + char *device_name, *device_tmp; struct binder_device *device; struct hlist_node *tmp; + char *device_names = NULL; ret = binder_alloc_shrinker_init(); if (ret) @@ -5917,6 +5918,10 @@ static int __init binder_init(void) } } + ret = init_binderfs(); + if (ret) + goto err_init_binder_device_failed; + return ret; err_init_binder_device_failed: diff --git a/drivers/android/binder_internal.h b/drivers/android/binder_internal.h index 7fb97f503ef2..045b3e42d98b 100644 --- a/drivers/android/binder_internal.h +++ b/drivers/android/binder_internal.h @@ -46,4 +46,13 @@ static inline bool is_binderfs_device(const struct inode *inode) } #endif +#ifdef CONFIG_ANDROID_BINDERFS +extern int __init init_binderfs(void); +#else +static inline int __init init_binderfs(void) +{ + return 0; +} +#endif + #endif /* _LINUX_BINDER_INTERNAL_H */ diff --git a/drivers/android/binderfs.c b/drivers/android/binderfs.c index 7a550104a722..e773f45d19d9 100644 --- a/drivers/android/binderfs.c +++ b/drivers/android/binderfs.c @@ -550,7 +550,7 @@ static struct file_system_type binder_fs_type = { .fs_flags = FS_USERNS_MOUNT, }; -static int __init init_binderfs(void) +int __init init_binderfs(void) { int ret; @@ -568,5 +568,3 @@ static int __init init_binderfs(void) return ret; } - -device_initcall(init_binderfs); -- cgit v1.2.3-55-g7522