当前位置:操作系统 > 安卓/Android >>

Android RIL源码研究笔记 の ril_event

Android源码目录hardware/ril/libril目录中总共包含5个C/CPP文件,它们分别是ril_commands.h、ril_unsol_commands.h、ril_event.h、ril_event.cpp和ril.cpp。这篇文章主要分析ril_event的相关代码。
   ril_event主要处理电话模块涉及的端口、modem等产生的事件,并将多个事件按时间顺序进行组织,并保存在事件队别中,主要使用了三个队列,分别是:watch_table[],timer_list和pending_list。代码是以C语言方式实现的,先来看头文件ril_event.h:
 
[cpp]
// 每次监视的最大的文件描述符句柄数,可以根据需要自行修改 
#define MAX_FD_EVENTS 8 
 
// ril_event的回调函数 
typedef void (*ril_event_cb)(int fd, short events, void *userdata); 
 
struct ril_event { 
    // 用于将ril_event串成双向链表的前向指针和后向指针 
    struct ril_event *next; 
    struct ril_event *prev; 
     
    //ril事件相关的文件描述符句柄(可以是文件、管道、Socket等) 
    int fd; 
     
    //这个事件在监控列表中的索引 
    int index; 
     
    //当一个事件处理完后(即从watch_table移到pending_list中等待处理), 
    //persist参数决定这个事件是否一直存在于监控列表watch_table[]中 
    bool persist; 
     
    //事件的超时时间 
    struct timeval timeout; 
     
    //回调函数及其传入的参数 
    ril_event_cb func; 
    void *param; 
}; 
 
//以下是ril事件相关的一些操作函数 
// 初始化内部数据结构 
void ril_event_init(); 
 
// 初始化一个ril事件 
void ril_event_set(struct ril_event * ev, int fd, bool persist, ril_event_cb func, void * param); 
 
// 将事件添加到监控列表watch_table[]中 
void ril_event_add(struct ril_event * ev); 
 
// 增加一个timer事件到timer_list链表中 
void ril_timer_add(struct ril_event * ev, struct timeval * tv); 
 
// 将指定的事件从监控列表watch_table[]中移除 
void ril_event_del(struct ril_event * ev); 
 
// 事件循环 
void ril_event_loop(); 

接着分析ril_event .cpp文件:
 
[cpp]
#define LOG_TAG "RILC" 
 
#include <stdlib.h> 
#include <unistd.h> 
#include <errno.h> 
#include <fcntl.h> 
#include <utils/Log.h> 
#include <ril_event.h> 
#include <string.h> 
#include <sys/time.h> 
#include <time.h> 
 
#include <pthread.h> 
 
// 使用互斥量mutex进行线程同步,可参见《Linux程序设计》相关章节 
static pthread_mutex_t listMutex; 
#define MUTEX_ACQUIRE() pthread_mutex_lock(&listMutex) 
#define MUTEX_RELEASE() pthread_mutex_unlock(&listMutex) 
#define MUTEX_INIT() pthread_mutex_init(&listMutex, NULL) 
#define MUTEX_DESTROY() pthread_mutex_destroy(&listMutex) 
 
// 两个timeval类型的值相加 
#ifndef timeradd 
#define timeradd(tvp, uvp, vvp)                     \ 
    do {                                \ 
        (vvp)->tv_sec = (tvp)->tv_sec + (uvp)->tv_sec;     \ 
        (vvp)->tv_usec = (tvp)->tv_usec + (uvp)->tv_usec;       \ 
        if ((vvp)->tv_usec >= 1000000) {          \ 
            (vvp)->tv_sec++;             \ 
            (vvp)->tv_usec -= 1000000;           \ 
        }                           \ 
    } while (0) 
#endif 
 
// 两个timeval类型的值进行比较 
#ifndef timercmp 
#define timercmp(a, b, op)               \ 
        ((a)->tv_sec == (b)->tv_sec      \ 
        ? (a)->tv_usec op (b)->tv_usec   \ 
        : (a)->tv_sec op (b)->tv_sec) 
#endif 
 
// 两个timeval类型的值相减 
#ifndef timersub 
#define timersub(a, b, res)                           \ 
    do {                                              \ 
        (res)->tv_sec = (a)->tv_sec - (b)->tv_sec;    \ 
        (res)->tv_usec = (a)->tv_usec - (b)->tv_usec; \ 
        if ((res)->tv_usec < 0) {                     \ 
            (res)->tv_usec += 1000000;                \ 
            (res)->tv_sec -= 1;                       \ 
        }                                             \ 
    } while(0); 
#endi 
 
// 保存Rild中所有设备文件句柄,便于使用select函数完成事件的监听 
static fd_set readFds; 
// 记录readFds中最大fd值+1 
static int nfds = 0; 
 
// 为了统一管理ril事件,Android提供如下三个队列: 
// 监控事件列表,需要检测的事件都需要先存入该列表中 
static struct ril_event * watch_table[MAX_FD_EVENTS]; 
 
// timer事件队列,事件超时后即移入pending_list队列中 
static struct ril_event timer_list; 

补充:移动开发 , Android ,
CopyRight © 2022 站长资源库 编程知识问答 zzzyk.com All Rights Reserved
部分文章来自网络,