ANDROID: binder: fix KMI issues due to frozen notification

The patches to support binder's frozen notification feature break the
KMI. This change fixes such issues by (1) moving proc->delivered_freeze
into the existing proc_wrapper struction, (2) dropping the frozen stats
support and (3) amending the STG due to a harmless enum binder_work_type
addition.

These are the reported KMI issues fixed by this patch:

  function symbol 'int __traceiter_binder_transaction_received(void*, struct binder_transaction*)' changed
    CRC changed from 0x74e9c98b to 0xfe0f8640

  type 'struct binder_proc' changed
    byte size changed from 584 to 632
    member 'struct list_head delivered_death' changed
      offset changed by 256
    member 'struct list_head delivered_freeze' was added
    13 members ('u32 max_threads' .. 'u64 android_oem_data1') changed
      offset changed by 384

  type 'struct binder_thread' changed
    byte size changed from 464 to 496
    2 members ('atomic_t tmp_ref' .. 'bool is_dead') changed
      offset changed by 224
    4 members ('struct task_struct* task' .. 'enum binder_prio_state prio_state') changed
      offset changed by 256

  type 'struct binder_stats' changed
    byte size changed from 216 to 244
    member changed from 'atomic_t br[21]' to 'atomic_t br[23]'
      type changed from 'atomic_t[21]' to 'atomic_t[23]'
        number of elements changed from 21 to 23
    member changed from 'atomic_t bc[19]' to 'atomic_t bc[22]'
      offset changed from 672 to 736
      type changed from 'atomic_t[19]' to 'atomic_t[22]'
        number of elements changed from 19 to 22
    member changed from 'atomic_t obj_created[7]' to 'atomic_t obj_created[8]'
      offset changed from 1280 to 1440
      type changed from 'atomic_t[7]' to 'atomic_t[8]'
        number of elements changed from 7 to 8
    member changed from 'atomic_t obj_deleted[7]' to 'atomic_t obj_deleted[8]'
      offset changed from 1504 to 1696
      type changed from 'atomic_t[7]' to 'atomic_t[8]'
        number of elements changed from 7 to 8

  type 'enum binder_work_type' changed
    enumerator 'BINDER_WORK_FROZEN_BINDER' (10) was added
    enumerator 'BINDER_WORK_CLEAR_FREEZE_NOTIFICATION' (11) was added

Bug: 363013421
Change-Id: If9f1f14a2eda215a4c9cb0823c50c8e0e8079ef1
Signed-off-by: Carlos Llamas <cmllamas@google.com>
This commit is contained in:
Carlos Llamas 2024-08-29 18:18:15 +00:00
parent 170220eae8
commit eec02eddcd
3 changed files with 18 additions and 17 deletions

View File

@ -284277,6 +284277,14 @@ enumeration {
name: "BINDER_WORK_CLEAR_DEATH_NOTIFICATION"
value: 9
}
enumerator {
name: "BINDER_WORK_FROZEN_BINDER"
value: 10
}
enumerator {
name: "BINDER_WORK_CLEAR_FREEZE_NOTIFICATION"
value: 11
}
}
}
enumeration {

View File

@ -4102,7 +4102,6 @@ binder_request_freeze_notification(struct binder_proc *proc,
is_frozen = ref->node->proc->is_frozen;
binder_inner_proc_unlock(ref->node->proc);
binder_stats_created(BINDER_STAT_FREEZE);
INIT_LIST_HEAD(&freeze->work.entry);
freeze->cookie = handle_cookie->cookie;
freeze->work.type = BINDER_WORK_FROZEN_BINDER;
@ -4188,7 +4187,7 @@ binder_freeze_notification_done(struct binder_proc *proc,
struct binder_work *w;
binder_inner_proc_lock(proc);
list_for_each_entry(w, &proc->delivered_freeze, entry) {
list_for_each_entry(w, &proc_wrapper(proc)->delivered_freeze, entry) {
struct binder_ref_freeze *tmp_freeze =
container_of(w, struct binder_ref_freeze, work);
@ -5157,7 +5156,7 @@ skip:
info.is_frozen = freeze->is_frozen;
info.cookie = freeze->cookie;
freeze->sent = true;
binder_enqueue_work_ilocked(w, &proc->delivered_freeze);
binder_enqueue_work_ilocked(w, &proc_wrapper(proc)->delivered_freeze);
binder_inner_proc_unlock(proc);
if (put_user(BR_FROZEN_BINDER, (uint32_t __user *)ptr))
@ -5177,7 +5176,6 @@ skip:
binder_inner_proc_unlock(proc);
kfree(freeze);
binder_stats_deleted(BINDER_STAT_FREEZE);
if (put_user(BR_CLEAR_FREEZE_NOTIFICATION_DONE, (uint32_t __user *)ptr))
return -EFAULT;
ptr += sizeof(uint32_t);
@ -6277,7 +6275,7 @@ static int binder_open(struct inode *nodp, struct file *filp)
binder_stats_created(BINDER_STAT_PROC);
proc->pid = current->group_leader->pid;
INIT_LIST_HEAD(&proc->delivered_death);
INIT_LIST_HEAD(&proc->delivered_freeze);
INIT_LIST_HEAD(&proc_wrapper(proc)->delivered_freeze);
INIT_LIST_HEAD(&proc->waiting_threads);
filp->private_data = proc;
@ -6838,8 +6836,6 @@ static const char * const binder_return_strings[] = {
"BR_FROZEN_REPLY",
"BR_ONEWAY_SPAM_SUSPECT",
"BR_TRANSACTION_PENDING_FROZEN",
"BR_FROZEN_BINDER",
"BR_CLEAR_FREEZE_NOTIFICATION_DONE",
};
static const char * const binder_command_strings[] = {
@ -6862,9 +6858,6 @@ static const char * const binder_command_strings[] = {
"BC_DEAD_BINDER_DONE",
"BC_TRANSACTION_SG",
"BC_REPLY_SG",
"BC_REQUEST_FREEZE_NOTIFICATION",
"BC_CLEAR_FREEZE_NOTIFICATION",
"BC_FREEZE_NOTIFICATION_DONE",
};
static const char * const binder_objstat_strings[] = {
@ -6875,7 +6868,6 @@ static const char * const binder_objstat_strings[] = {
"death",
"transaction",
"transaction_complete",
"freeze",
};
static void print_binder_stats(struct seq_file *m, const char *prefix,

View File

@ -131,13 +131,12 @@ enum binder_stat_types {
BINDER_STAT_DEATH,
BINDER_STAT_TRANSACTION,
BINDER_STAT_TRANSACTION_COMPLETE,
BINDER_STAT_FREEZE,
BINDER_STAT_COUNT
};
struct binder_stats {
atomic_t br[_IOC_NR(BR_CLEAR_FREEZE_NOTIFICATION_DONE) + 1];
atomic_t bc[_IOC_NR(BC_FREEZE_NOTIFICATION_DONE) + 1];
atomic_t br[_IOC_NR(BR_TRANSACTION_PENDING_FROZEN) + 1];
atomic_t bc[_IOC_NR(BC_REPLY_SG) + 1];
atomic_t obj_created[BINDER_STAT_COUNT];
atomic_t obj_deleted[BINDER_STAT_COUNT];
};
@ -162,8 +161,10 @@ struct binder_work {
BINDER_WORK_DEAD_BINDER,
BINDER_WORK_DEAD_BINDER_AND_CLEAR,
BINDER_WORK_CLEAR_DEATH_NOTIFICATION,
#ifndef __GENKSYMS__
BINDER_WORK_FROZEN_BINDER,
BINDER_WORK_CLEAR_FREEZE_NOTIFICATION,
#endif
} type;
ANDROID_OEM_DATA(1);
@ -419,8 +420,6 @@ enum binder_prio_state {
* (atomics, no lock needed)
* @delivered_death: list of delivered death notification
* (protected by @inner_lock)
* @delivered_freeze: list of delivered freeze notification
* (protected by @inner_lock)
* @max_threads: cap on number of binder threads
* (protected by @inner_lock)
* @requested_threads: number of binder threads requested but not
@ -467,7 +466,6 @@ struct binder_proc {
struct list_head todo;
struct binder_stats stats;
struct list_head delivered_death;
struct list_head delivered_freeze;
u32 max_threads;
int requested_threads;
int requested_threads_started;
@ -488,10 +486,13 @@ struct binder_proc {
* @proc: binder_proc being wrapped
* @dmap dbitmap to manage available reference descriptors
* (protected by @proc.outer_lock)
* @delivered_freeze: list of delivered freeze notification
* (protected by @inner_lock)
*/
struct binder_proc_wrap {
struct binder_proc proc;
struct dbitmap dmap;
struct list_head delivered_freeze;
};
static inline