diff options
Diffstat (limited to 'drivers/android/binder.c')
-rw-r--r-- | drivers/android/binder.c | 29 |
1 files changed, 23 insertions, 6 deletions
diff --git a/drivers/android/binder.c b/drivers/android/binder.c index 15e3d3c2260d..764b63a5aade 100644 --- a/drivers/android/binder.c +++ b/drivers/android/binder.c | |||
@@ -1991,8 +1991,14 @@ static void binder_send_failed_reply(struct binder_transaction *t, | |||
1991 | &target_thread->reply_error.work); | 1991 | &target_thread->reply_error.work); |
1992 | wake_up_interruptible(&target_thread->wait); | 1992 | wake_up_interruptible(&target_thread->wait); |
1993 | } else { | 1993 | } else { |
1994 | WARN(1, "Unexpected reply error: %u\n", | 1994 | /* |
1995 | target_thread->reply_error.cmd); | 1995 | * Cannot get here for normal operation, but |
1996 | * we can if multiple synchronous transactions | ||
1997 | * are sent without blocking for responses. | ||
1998 | * Just ignore the 2nd error in this case. | ||
1999 | */ | ||
2000 | pr_warn("Unexpected reply error: %u\n", | ||
2001 | target_thread->reply_error.cmd); | ||
1996 | } | 2002 | } |
1997 | binder_inner_proc_unlock(target_thread->proc); | 2003 | binder_inner_proc_unlock(target_thread->proc); |
1998 | binder_thread_dec_tmpref(target_thread); | 2004 | binder_thread_dec_tmpref(target_thread); |
@@ -2193,7 +2199,7 @@ static void binder_transaction_buffer_release(struct binder_proc *proc, | |||
2193 | int debug_id = buffer->debug_id; | 2199 | int debug_id = buffer->debug_id; |
2194 | 2200 | ||
2195 | binder_debug(BINDER_DEBUG_TRANSACTION, | 2201 | binder_debug(BINDER_DEBUG_TRANSACTION, |
2196 | "%d buffer release %d, size %zd-%zd, failed at %p\n", | 2202 | "%d buffer release %d, size %zd-%zd, failed at %pK\n", |
2197 | proc->pid, buffer->debug_id, | 2203 | proc->pid, buffer->debug_id, |
2198 | buffer->data_size, buffer->offsets_size, failed_at); | 2204 | buffer->data_size, buffer->offsets_size, failed_at); |
2199 | 2205 | ||
@@ -3705,7 +3711,7 @@ static int binder_thread_write(struct binder_proc *proc, | |||
3705 | } | 3711 | } |
3706 | } | 3712 | } |
3707 | binder_debug(BINDER_DEBUG_DEAD_BINDER, | 3713 | binder_debug(BINDER_DEBUG_DEAD_BINDER, |
3708 | "%d:%d BC_DEAD_BINDER_DONE %016llx found %p\n", | 3714 | "%d:%d BC_DEAD_BINDER_DONE %016llx found %pK\n", |
3709 | proc->pid, thread->pid, (u64)cookie, | 3715 | proc->pid, thread->pid, (u64)cookie, |
3710 | death); | 3716 | death); |
3711 | if (death == NULL) { | 3717 | if (death == NULL) { |
@@ -4376,6 +4382,15 @@ static int binder_thread_release(struct binder_proc *proc, | |||
4376 | 4382 | ||
4377 | binder_inner_proc_unlock(thread->proc); | 4383 | binder_inner_proc_unlock(thread->proc); |
4378 | 4384 | ||
4385 | /* | ||
4386 | * This is needed to avoid races between wake_up_poll() above and | ||
4387 | * and ep_remove_waitqueue() called for other reasons (eg the epoll file | ||
4388 | * descriptor being closed); ep_remove_waitqueue() holds an RCU read | ||
4389 | * lock, so we can be sure it's done after calling synchronize_rcu(). | ||
4390 | */ | ||
4391 | if (thread->looper & BINDER_LOOPER_STATE_POLL) | ||
4392 | synchronize_rcu(); | ||
4393 | |||
4379 | if (send_reply) | 4394 | if (send_reply) |
4380 | binder_send_failed_reply(send_reply, BR_DEAD_REPLY); | 4395 | binder_send_failed_reply(send_reply, BR_DEAD_REPLY); |
4381 | binder_release_work(proc, &thread->todo); | 4396 | binder_release_work(proc, &thread->todo); |
@@ -4391,6 +4406,8 @@ static __poll_t binder_poll(struct file *filp, | |||
4391 | bool wait_for_proc_work; | 4406 | bool wait_for_proc_work; |
4392 | 4407 | ||
4393 | thread = binder_get_thread(proc); | 4408 | thread = binder_get_thread(proc); |
4409 | if (!thread) | ||
4410 | return POLLERR; | ||
4394 | 4411 | ||
4395 | binder_inner_proc_lock(thread->proc); | 4412 | binder_inner_proc_lock(thread->proc); |
4396 | thread->looper |= BINDER_LOOPER_STATE_POLL; | 4413 | thread->looper |= BINDER_LOOPER_STATE_POLL; |
@@ -5034,7 +5051,7 @@ static void print_binder_transaction_ilocked(struct seq_file *m, | |||
5034 | spin_lock(&t->lock); | 5051 | spin_lock(&t->lock); |
5035 | to_proc = t->to_proc; | 5052 | to_proc = t->to_proc; |
5036 | seq_printf(m, | 5053 | seq_printf(m, |
5037 | "%s %d: %p from %d:%d to %d:%d code %x flags %x pri %ld r%d", | 5054 | "%s %d: %pK from %d:%d to %d:%d code %x flags %x pri %ld r%d", |
5038 | prefix, t->debug_id, t, | 5055 | prefix, t->debug_id, t, |
5039 | t->from ? t->from->proc->pid : 0, | 5056 | t->from ? t->from->proc->pid : 0, |
5040 | t->from ? t->from->pid : 0, | 5057 | t->from ? t->from->pid : 0, |
@@ -5058,7 +5075,7 @@ static void print_binder_transaction_ilocked(struct seq_file *m, | |||
5058 | } | 5075 | } |
5059 | if (buffer->target_node) | 5076 | if (buffer->target_node) |
5060 | seq_printf(m, " node %d", buffer->target_node->debug_id); | 5077 | seq_printf(m, " node %d", buffer->target_node->debug_id); |
5061 | seq_printf(m, " size %zd:%zd data %p\n", | 5078 | seq_printf(m, " size %zd:%zd data %pK\n", |
5062 | buffer->data_size, buffer->offsets_size, | 5079 | buffer->data_size, buffer->offsets_size, |
5063 | buffer->data); | 5080 | buffer->data); |
5064 | } | 5081 | } |