Android的無(wú)線(xiàn)接口層(RIL)提供了Android電話(huà)服務(wù)(android.telephony)與無(wú)線(xiàn)電硬件之間的抽象層。RIL是通訊無(wú)關(guān)的,,提供基于GSM的網(wǎng)絡(luò)支持,。
下圖顯示了RIL位于Android電話(huà)系統(tǒng)架構(gòu)中的位置:
實(shí)線(xiàn)框表示Android部分,虛線(xiàn)框表示合作伙伴所專(zhuān)用的部分
RIL包含兩個(gè)基本部件:
RIL守護(hù)進(jìn)程(RIL Daemon):RIL守護(hù)進(jìn)程初始化Vendor RIL,,管理所有來(lái)自Android通訊服務(wù)的通訊,,將其作為被請(qǐng)求的命令(solicited commands)調(diào)度給Vendor RIL。
Vendor RIL:ril.h文件中的無(wú)線(xiàn)電專(zhuān)用Vendor RIL掌管著所有和無(wú)線(xiàn)電硬件的通訊,,并且通過(guò)未被請(qǐng)求的命令(unsolicited commands)分發(fā)給RIL 守護(hù)進(jìn)程,。
RIL初始化:
Android在啟動(dòng)時(shí)初始化通訊棧和Vendor RIL,描述如下:
1. RIL守護(hù)進(jìn)程讀取rild.lib路徑和rild.libargs系統(tǒng)參數(shù),,決定應(yīng)該使用的Vendor RIL庫(kù)和向Vendor RIL提供的初始化參數(shù)
2. RIL守護(hù)進(jìn)程加載Vendor RIL庫(kù),,執(zhí)行RIL_Init初始化RIL并為RIL函數(shù)獲取參數(shù)
3. RIL守護(hù)進(jìn)程調(diào)用Android通訊棧中RIL_register,,為Vendor RIL函數(shù)提供參考。
RIL守護(hù)進(jìn)程源碼請(qǐng)參考:/device/commands/rild/rild.c
RIL 交互:
RIL句柄提供了兩種交互方式:
主動(dòng)請(qǐng)求命令(Solicited commands):主動(dòng)請(qǐng)求命令來(lái)自RIL lib,,比如DIAL和HANGUP,。
被動(dòng)請(qǐng)求命令(Unsolicited responses):被動(dòng)請(qǐng)求命令來(lái)自基帶,比如CALL_STATE_CHANGED 和 NEW_SMS,。
主動(dòng)請(qǐng)求:
以下代碼片段屬于主動(dòng)請(qǐng)求命令
void OnRequest (int request_id, void *data, size_t datalen, RIL_Token t);
void OnRequestComplete (RIL_Token t, RIL_Error e, void *response, size_t responselen);
有超過(guò)60個(gè)主動(dòng)請(qǐng)求命令:
* SIM PIN,,IO和IMSI/IMEI(11)
* 電話(huà)狀態(tài)和動(dòng)作(撥號(hào),應(yīng)答,,靜音…)(16)
* 網(wǎng)絡(luò)狀態(tài)查詢(xún)(4)
* 網(wǎng)絡(luò)設(shè)置(禁止,,轉(zhuǎn)發(fā),選擇…)(12)
* 短信(3)
* PDP連接(4)
* 電源和復(fù)位(2)
* 輔助服務(wù)(5)
* 供應(yīng)商定義及其支持(4)
下圖表明了Android系統(tǒng)一個(gè)主動(dòng)請(qǐng)求的電話(huà)過(guò)程:
被動(dòng)請(qǐng)求:
以下代碼片段屬于被動(dòng)請(qǐng)求命令
void OnUnsolicitedResponse (int unsolResponse, void *data, size_t datalen);
有超過(guò)10條被動(dòng)請(qǐng)求命令:
* 網(wǎng)絡(luò)狀態(tài)改變(4)
* 新短信通知(3)
* 新USSD通知(2)
* 信號(hào)強(qiáng)度和時(shí)間改變(2)
下圖表明Android系統(tǒng)中一個(gè)被動(dòng)請(qǐng)求的電話(huà)過(guò)程:
實(shí)現(xiàn)RIL:
為了實(shí)現(xiàn)一個(gè)通訊專(zhuān)用RIL,,需要執(zhí)行一系列函數(shù)以創(chuàng)建一個(gè)共享庫(kù),,保證Android能夠相應(yīng)無(wú)線(xiàn)通信請(qǐng)求。所需要的函數(shù)被定義在RIL頭部(/include/telephony/ril.h)
Android通訊接口是通訊無(wú)關(guān)的,,Vendor RIL可以使用任意協(xié)議進(jìn)行無(wú)線(xiàn)通訊,。Android提供了一個(gè)參考Vendor RIL,使用的是賀式(Hayes)AT命令設(shè)備,,可作為一個(gè)商用的快速入門(mén)指導(dǎo)以及通訊測(cè)試使用,。
RIL參考源碼在/commands/reference-ril/。
通常將你自己的Vendor RIL編譯為以下形式:
libril-<companyname>-<RIL version>.so
比如:
libril-acme-124.so
其中:
libril:所有vendor RIL的開(kāi)頭,;
<companyname>:專(zhuān)用公司縮寫(xiě)
<RIL version>:RIL版本number
so:文件擴(kuò)展
RIL初始化:
特定的Vendor RIL必須定義一個(gè)初始化函數(shù),,提供一系列句柄函數(shù)以處理每一個(gè)通訊請(qǐng)求。Android RIL守護(hù)進(jìn)程會(huì)在啟動(dòng)時(shí)調(diào)用RIL_Init以初始化RIL,。
RIL_RadioFunctions *RIL_Init (RIL_Env* env, int argc, char **argv);
RIL_Init 返回一個(gè)RIL_RadioFunctions結(jié)構(gòu)體包含無(wú)線(xiàn)電函數(shù)指針,。
type structure {
int RIL_version;
RIL_RequestFunc onRequest;
RIL_RadioStateRequest onStateRequest;
RIL_Supports supports;
RIL_Cancel onCancel;
RIL_GetVersion getVersion;
} RIL_RadioFunctions;
RIL函數(shù):
ril.h定義了RIL狀態(tài)和變量,比如RIL_UNSOL_STK_CALL_SETUP, RIL_SIM_READY, RIL_SIM_NOT_READY,,具體函數(shù)描述見(jiàn)下表,。忽略頭文件細(xì)節(jié)。
RIL主動(dòng)命令請(qǐng)求
Vendor RIL必須提供下表中的函數(shù)用以發(fā)送主動(dòng)命令,。RIL主動(dòng)命令請(qǐng)求類(lèi)型定義在ril.h的RIL_REQUEST_prefix中,。
void (*RIL_RequestFunc) (int request, void *data, size_t datalen, RIL_Token t);
RIL主動(dòng)命令入口指針,,必須能夠處理各種RIL主動(dòng)請(qǐng)求(定義于ril.h的RIL_REQUEST_ prefix)
* request 是一種 RIL_REQUEST_*
* data 是一個(gè)指向RIL_REQUEST_*數(shù)據(jù)的指針
* t 應(yīng)當(dāng)被用于RIL_onResponse的后續(xù)調(diào)用
* datalen 由調(diào)用者所有,,應(yīng)當(dāng)由被調(diào)者修改或釋放
必須調(diào)用RIL_onRequestComplete()函數(shù)完成通訊。?RIL_onRequestComplete() 在這個(gè)函數(shù)返回前或之后可能被任意線(xiàn)程調(diào)用,。這個(gè)函數(shù)總會(huì)調(diào)用同一個(gè)線(xiàn)程,,因此返回到這里意味著無(wú)線(xiàn)通訊準(zhǔn)備去處理其他命令(無(wú)論前面命令是否完成傳輸)。
RIL_RadioState (*RIL_RadioStateRequest)();
這個(gè)函數(shù)應(yīng)該返回當(dāng)前通訊同步狀態(tài)
int (*RIL_Supports)(int requestCode);
如果提供指定RIL_REQUEST代碼,返回1,,否則返回0.
void (*RIL_Cancel)(RIL_Token t);
本函數(shù)用來(lái)指示取消一個(gè)待處理請(qǐng)求。函數(shù)將被一個(gè)獨(dú)立線(xiàn)程所調(diào)用,,而不是RIL_RequestFunc函數(shù),。
一旦取消,被調(diào)用者應(yīng)當(dāng)盡量放棄請(qǐng)求并在這之后調(diào)用RIL_onRequestComplete 函數(shù)的RIL_Errno CANCELLED ,。
響應(yīng)請(qǐng)求后調(diào)用 RIL_onRequestComplete 并產(chǎn)生其他結(jié)果是可以被接受的,,但會(huì)被忽略(理應(yīng)忽略被取消的請(qǐng)求)。
RIL_Cancel 調(diào)用應(yīng)該被立刻返回,,不需要等待取消,。
const char * (*RIL_GetVersion) (void);
向你的Vendor RIL返回版本字符串
Vendor RIL使用以下回調(diào)函數(shù)與Android RIL守護(hù)進(jìn)程通訊。
void RIL_onRequestComplete(RIL_Token t, RIL_Errno e, void *response, size_t responselen);
* t 是之前通訊傳遞至RIL_Notification的參數(shù)
* 如果e != SUCCESS,,則可以沒(méi)有相應(yīng),,并且被忽略
* response 由調(diào)用者所有,應(yīng)當(dāng)由被調(diào)用者修改或者釋放,。
* RIL_onRequestComplete 將盡快返回
void RIL_requestTimedCallback (RIL_TimedCallback callback, void *param, const struct timeval *relativeTime);
用戶(hù)指定的回調(diào)函數(shù)的線(xiàn)程中,,RIL_RequestFunc 函數(shù)被調(diào)用。如果指定了relativeTime,,那么回調(diào)前將等待一個(gè)一個(gè)特定的時(shí)間值,。如果 relativeTime 為空,或者指針指向了一個(gè)空的結(jié)構(gòu)體,,回調(diào)函數(shù)會(huì)盡快被執(zhí)行,。
RIL被動(dòng)命令
下表函數(shù)是Vedor RIL使用的回調(diào)函數(shù),用來(lái)喚醒被動(dòng)命令在Android平臺(tái)的相應(yīng)機(jī)制,。
void RIL_onUnsolicitedResponse(int unsolResponse, const void *data, size_t datalen);
* unsolResponse 是 RIL_UNSOL_RESPONSE_* 其中之一
* data 是指向RIL_UNSOL_RESPONSE_*數(shù)據(jù)的指針
* data被調(diào)用者所有,,應(yīng)當(dāng)由被調(diào)用者修改或者釋放