浅析android下native层binder的部分具体实现
在defaultServiceManager( ) 方法中:[ luther. gliethttp]
= = > defaultServiceManager
= = >
sp< IServiceManager> gDefaultServiceManager; 的m_ptr指向new BpServiceManager( obj) ; 因为= 这个操作符被sp类模板重载
这个obj就是ProcessState: : self( ) - > getContextObject( NULL ) 返回的gProcess.
sp< ProcessState> gProcess; 的m_ptr指向new BpBinder( handle) ; [ ProcessState: : self( ) 函数返回] 因为= 这个操作符被sp类模板重载
看看BpServiceManager构造函数:
BpServiceManager( const sp< IBinder> & impl)
: BpInterface< IServiceManager> ( impl)
{
}
template < typename INTERFACE>
inline BpInterface< INTERFACE> : : BpInterface( const sp< IBinder> & remote)
: BpRefBase( remote)
{
}
BpRefBase: : BpRefBase( const sp< IBinder> & o)
: mRemote( o. get( ) ) , mRefs( NULL ) , mState( 0) //这里o.get()就是gProcess.get(),返回gProcess指向new BpBinder(handle);的m_ptr
{ //mRemote在类IBinder中的定义:IBinder* const mRemote;[luther.gliethttp]
extendObjectLifetime( OBJECT_LIFETIME_WEAK) ;
if ( mRemote) {
mRemote- > incStrong( this ) ; // Removed on first IncStrong().
mRefs = mRemote- > createWeak( this ) ; // Held for our entire lifetime.
}
}
remote( ) - > transact( ADD_SERVICE_TRANSACTION, data, & reply) ;
这里的remote来自inline IBinder* remote( ) { return mRemote; }
因为mRemote为IBinder类的指针, - > 操作符没有被重载, 所以就是调用BpBinder: : transact方法[ luther. gliethttp]
status_t BpBinder: : transact(
uint32_t code, const Parcel& data, Parcel* reply, uint32_t flags)
{
// Once a binder has died, it will never come back to life.
if ( mAlive) {
status_t status = IPCThreadState: : self( ) - > transact(
mHandle, code, data, reply, flags) ;
if ( status = = DEAD_OBJECT) mAlive = 0;
return status;
}
return DEAD_OBJECT;
}
status_t flatten_binder( const sp< ProcessState> & proc,
const sp< IBinder> & binder, Parcel* out)
{
flat_binder_object obj;
obj. flags = 0x7f | FLAT_BINDER_FLAG_ACCEPTS_FDS;
if ( binder ! = NULL ) {
IBinder * local = binder- > localBinder( ) ;
//对于BBinder* BBinder::localBinder()
//{
// return this;
//}
//对于BBinder* IBinder::localBinder()
//{
// return NULL;
//}
if ( ! local) {
BpBinder * proxy = binder- > remoteBinder( ) ;
if ( proxy = = NULL ) {
LOGE( "null proxy" ) ;
}
const int32_t handle = proxy ? proxy- > handle( ) : 0;
obj. type = BINDER_TYPE_HANDLE;
obj. handle = handle;
obj. cookie = NULL ;
} else { //对于IServiceManager::addService将执行到这里
obj. type = BINDER_TYPE_BINDER;
obj. binder = local- > getWeakRefs( ) ; //作为红黑节点树的唯一id标号
obj. cookie = local;
}
} else {
obj. type = BINDER_TYPE_BINDER;
obj. binder = NULL ;
obj. cookie = NULL ;
}
return finish_flatten_binder( binder, obj, out) ;
}
commands/ binder/ service_manager. c
= > svcmgr_handler
= > do_add_service
commands/ binder/ service_manager. c
= = > main
= = > bs = binder_open( 128* 1024) ;
//proc->tsk = current;
//filp->private_data = proc;
= = > binder_become_context_manager( bs) ; //将bs作为context_manager管理binder,发送ioctl(bs->fd, BINDER_SET_CONTEXT_MGR, 0);
//这样binder驱动的binder_context_mgr_node就是该bs了
= = > binder_loop( bs, svcmgr_handler) ; //回调函数svcmgr_handler,用来处理消息
void binder_loop( struct binder_state * bs, binder_handler func)
{
. . .
readbuf[ 0] = BC_ENTER_LOOPER;
binder_write( bs, readbuf, sizeof ( unsigned ) ) ;
//thread->looper |= BINDER_LOOPER_STATE_ENTERED;
//struct binder_thread *thread = binder_get_thread()会查找该proc自己是否已经在binder_thread,
//rb_link_node(&thread->rb_node, parent, p);
//rb_insert_color(&thread->rb_node, &proc->threads);将该current[就是proc打开者自己]绑定到binder_thread,然后插入到proc管理的红黑树中.
//proc管理的红黑树的索引依据为pid数值:thread->pid = current->pid;
/*
*struct binder_stats {
int br[_IOC_NR(BR_FAILED_REPLY) + 1];
int bc[_IOC_NR(BC_DEAD_BINDER_DONE) + 1];
int obj_created[BINDER_STAT_COUNT];
int obj_deleted[BINDER_STAT_COUNT];
};
static struct binder_stats binder_stats;
* */
for ( ; ; ) {
. . .
bwr. read_size = sizeof ( readbuf) ;
bwr. read_consumed = 0;
bwr. read_buffer = ( unsigned ) readbuf;
//wait_for_proc_work = thread->transaction_stack == NULL && list_empty(&thread->todo);
//没有todo的咚咚
res = ioctl( bs- > fd, BINDER_WRITE_READ, & bwr) ;
//首先binder推入4字节的BR_NOOP控制头
. . .
res = binder_parse( bs, 0, readbuf, bwr. read_consumed, func) ;
. . .
}
. . .
}
driver中
device_initcall( binder_init) ;
= > binder_init
= > 创建/ proc/ binder根目录
= > 创建/ proc/ binder/ proc目录
= > misc_register( & binder_miscdev) ; 注册/ dev/ binder字符设备文件
= > 该/ dev/ binder节点由init进程在handle_device_fd( device_fd) ; = = > handle_device_event( & uevent) ; 中uevent- netlink处理之后, "/dev/" 目录下创建.
= > 创建只读文件"state" 、"stats" 、"transactions" 、"transaction_log" 和"failed_transaction_log" ,
帮定读文件函数binder_read_proc_stats
这样binder驱动在内核中登记工作就完成了, 剩下的工作就是应用程序使用这个binder进行IPC了.
if ( tr- > target. handle) { //目的handle
struct binder_ref * ref;
ref = binder_get_ref( proc, tr- > target. handle) ; //返回目的handle的ref,该handle由后面的binder_get_ref_for_node()函数生成
if ( ref = = NULL ) {
binder_user_error( "binder: %d:%d got "
"transaction to invalid handle/n" ,
proc- > pid, thread- > pid) ;
return_error = BR_FAILED_REPLY;
goto err_invalid_target_handle;
}
target_node = ref- > node;
} else {
target_node = binder_context_mgr_node;
if ( target_node = = NULL ) {
return_error = BR_DEAD_REPLY;
goto err_no_context_mgr_node;
}
}
static struct binder_ref *
binder_get_ref( struct binder_proc * proc, uint32_t desc)
{
struct rb_node * n = proc- > refs_by_desc. rb_node; //是否有该desc对应的内容
struct binder_ref * ref;
while ( n) {
ref = rb_entry( n, struct binder_ref, rb_node_desc) ;
if ( desc < ref- > desc)
n = n- > rb_left;
else if ( desc > ref- > desc)
n = n- > rb_right;
else
return ref;
}
return NULL ;
}
struct flat_binder_object {
/* 8 bytes for large_flat_header. */
unsigned long type;
unsigned long flags;
/* 8 bytes of data. */
union {
void * binder; /* local object */
signed long handle; /* remote object */
} ;
/* extra data associated with local object */
void * cookie;
} ;
= = > binder_transaction
= = > struct flat_binder_object * fp;
. . .
switch ( fp- > type) {
case BINDER_TYPE_BINDER:
case BINDER_TYPE_WEAK_BINDER: {
struct binder_ref * ref;
//上面obj.binder = local->getWeakRefs();//作为红黑节点树的唯一id标号,所以这里从红黑树上查找fp->binder节点[luther.gliethttp]
struct binder_node * node = binder_get_node( proc, fp- > binder) ; //如果从红黑树中没有找到,那么
if ( node = = NULL ) {
node = binder_new_node( proc, fp- > binder, fp- > cookie) ; //创建一个新的node
if ( node = = NULL ) {
return_error = BR_FAILED_REPLY;
goto err_binder_new_node_failed;
}
node- > min_priority = fp- > flags & FLAT_BINDER_FLAG_PRIORITY_MASK;
node- > accept_fds = ! ! ( fp- > flags & FLAT_BINDER_FLAG_ACCEPTS_FDS) ;
}
if ( fp- > cookie ! = node- > cookie) {
binder_user_error( "binder: %d:%d sending u%p "
"node %d, cookie mismatch %p != %p/n" ,
proc- > pid, thread- > pid,
fp- > binder, node- > debug_id,
fp- > cookie, node- > cookie) ;
goto err_binder_get_ref_for_node_failed;
}
ref = binder_get_ref_for_node( target_proc, node) ; //将新创建的node挂接到红黑树上
if ( ref = = NULL ) {
return_error = BR_FAILED_REPLY;
goto err_binder_get_ref_for_node_failed;
}
if ( fp- > type = = BINDER_TYPE_BINDER)
fp- > type = BINDER_TYPE_HANDLE;
else
fp- > type = BINDER_TYPE_WEAK_HANDLE;
fp- > handle = ref- > desc; //获取唯一id号,作为handle用来区分service们
binder_inc_ref( ref, fp- > type = = BINDER_TYPE_HANDLE, & thread- > todo) ;
if ( binder_debug_mask & BINDER_DEBUG_TRANSACTION)
printk( KERN_INFO " node %d u%p -> ref %d desc %d/n" ,
node- > debug_id, node- > ptr, ref- > debug_id, ref- > desc) ;
} break ;
case BINDER_TYPE_HANDLE:
case BINDER_TYPE_WEAK_HANDLE: {
. . .
new_ref = binder_get_ref_for_node( target_proc, ref- > node) ;
. . .
= = > binder_thread_write
= = > if ( target = = 0 & & binder_context_mgr_node & &
( cmd = = BC_INCREFS | | cmd = = BC_ACQUIRE) ) {
ref = binder_get_ref_for_node( proc,
binder_context_mgr_node) ;
static struct binder_ref *
binder_get_ref_for_node( struct binder_proc * proc, struct binder_node * node)
{
. . .
rb_insert_color( & new_ref- > rb_node_desc, & proc- > refs_by_desc) ;
new_ref- > desc = ( node = = binder_context_mgr_node) ? 0 : 1;
for ( n = rb_first( & proc- > refs_by_desc) ; n ! = NULL ; n = rb_next( n) ) {
ref = rb_entry( n, struct binder_ref, rb_node_desc) ;
if ( ref- > desc > new_ref- > desc)
break ;
new_ref- > desc = ref- > desc + 1; //计算service们对应的唯一handle号[luther.gliethttp]
}
. . .
}
浅析android下native层binder的部分具体实现
最新推荐文章于 2023-07-07 09:45:04 发布