當(dāng)前位置:首頁 > IT技術(shù) > 移動平臺 > 正文

Android原生Property移植記錄
2021-11-16 11:38:04


Android原生Property移植記錄_客戶端



簡介

屬性系統(tǒng)是Android的一個重要特性,屬性由屬性名稱和鍵值組成的一段字符串,又稱鍵值對,用于記錄系統(tǒng)設(shè)置或進(jìn)程信息交換。屬性在整個系統(tǒng)全局可見,每個進(jìn)程可通過property_get/property_set獲取和設(shè)置屬性。本篇主要介紹移植版本的Property大致流程。

Property機(jī)制主要由服務(wù)端進(jìn)程與客戶端進(jìn)程組成。property服務(wù)端進(jìn)程用于初始化存儲屬性的共享空間、監(jiān)聽客戶端請求、增加屬性鍵值對和更新屬性對應(yīng)鍵值等功能??蛻舳藶槭褂肞roperty的應(yīng)用進(jìn)程,主要通過調(diào)用poperty_set和property_get集來實現(xiàn)設(shè)置和獲取屬性鍵值。

移植版本Property與Android原生Property使用方法有一些區(qū)別:

(1) Android是在init進(jìn)程初始化Property服務(wù)端。移植版本則將Property服務(wù)端設(shè)計為獨立進(jìn)程,在開機(jī)啟動時啟用Property服務(wù)。如此設(shè)計的優(yōu)點在于,將Property服務(wù)設(shè)計為獨立的模塊,便于各個應(yīng)用移植和使用。

(2) Android在使用Property機(jī)制時會核對使用進(jìn)程Selinux權(quán)限,在進(jìn)程使用property_set/property_get時,會先審核使用進(jìn)程是否擁有訪問該屬性權(quán)限。移植版本Property則省去Selinux權(quán)限。

(3) 移植版本Property是在Android KitKat4.4基礎(chǔ)上移植而來,其內(nèi)部實現(xiàn)細(xì)節(jié)可能與4.4版本之后有所出入。

API介紹

服務(wù)端:

本部分代碼接口無需特殊關(guān)注,只需將編譯的bin文件(Property_service)放入起始服務(wù)后臺運行即可。Property服務(wù)端代碼執(zhí)行順序需優(yōu)先于客戶端。

客戶端:

客戶端代碼主要功能為設(shè)置和獲取Property鍵值,以下為對外開放的接口。

設(shè)置Property

/*
* @description: 設(shè)置或增加屬性鍵值
* @param - key: 需設(shè)置的屬性名。
* @param - value: 屬性名對應(yīng)的鍵值。
* @return: 0 on success,< 0 on failure
*/int property_set(const char *key, const char *value)


獲取Property

/*
* @description: 獲取屬性鍵值字符串
* @param - key: 需獲取的屬性名。
* @param - value: 屬性名對應(yīng)的鍵值。
* @param - default_value: 若獲取失敗,則使用此默認(rèn)鍵值
* @return: 成功返回屬性值長度,獲取錯誤返回0
*/int property_get(const char *key, char *value, const char *default_value)
/*
* @description:用于獲取bool類型的屬性,失敗返回默認(rèn)值default_value
*/int8_t property_get_bool(const char *key, int8_t default_value)
/*
* @description:用于獲取64位類型的屬性,失敗返回默認(rèn)值default_value
*/int64_t property_get_int64(const char *key, int64_t default_value)
/*
* @description:用于獲取32位類型的屬性,失敗返回默認(rèn)值default_value
*/int32_t property_get_int32(const char *key, int32_t default_value)


注:系統(tǒng)中存在的key字符長度最大為32,value字符長度最大為92。如有越過,會導(dǎo)致異常情況。

特殊類型屬性:

“ro.”前綴:?“ro.”前綴,只讀屬性。僅會被設(shè)置一次,即當(dāng)設(shè)置此屬性發(fā)現(xiàn)其屬性名已經(jīng)存在,則此次設(shè)置不會生效,返回-1。

“persist.”前綴:?“persist.”前綴,保留屬性。當(dāng)服務(wù)端接收到persist屬性設(shè)置請求時,會在/data/property目錄下建立對應(yīng)的屬性文件,并將鍵值存儲到此文件中。如此一來即可實現(xiàn)鍵值掉電存儲功能。

實現(xiàn)機(jī)制

流程:簡單的介紹,Property機(jī)制運作流程可以簡單的概括為以下幾步:

  • PropertyService服務(wù)啟動,初始化共享內(nèi)存,加載若干屬性腳本中默認(rèn)屬性內(nèi)容;
  • 將系統(tǒng)中所有屬性內(nèi)容(key/value)存入系統(tǒng)共享內(nèi)存,創(chuàng)建socket,并持續(xù)監(jiān)聽客戶端socket請求;
  • 系統(tǒng)中各個客戶進(jìn)程將共享內(nèi)存(只讀權(quán)限)映射到自己的內(nèi)存空間,可直接讀取屬性內(nèi)容;
  • 系統(tǒng)僅有Property Service (屬性服務(wù))可修改和增加屬性值;
  • 各個客戶進(jìn)程僅有讀取屬性權(quán)限,如需修改屬性,需通過socket方式向Property Service發(fā)出修改請求,由Property Service統(tǒng)一修改;
  • 屬性鍵值內(nèi)容以字典樹的形式存儲于共享內(nèi)存中(二叉樹)。

Property機(jī)制示意圖:Android原生Property移植記錄_android_02

代碼分析:

  • Property Service:Property服務(wù)端實現(xiàn)內(nèi)容主要包括兩部分:存儲屬性值共享內(nèi)存(mmap + 二叉樹)和建立通信(socket)。?共享機(jī)制:將文件映射兩次到內(nèi)存,第一次為可讀可寫權(quán)限,句柄為property service服務(wù);第二次為只讀權(quán)限,句柄為client服務(wù)。?通信機(jī)制:服務(wù)端建立socket通信,持續(xù)監(jiān)聽并處理客戶端請求。Android原生Property移植記錄_android_03
  • Property Client:
    客戶端功能主要為設(shè)置屬性和獲取屬性。其中獲取屬性可直接讀取共享內(nèi)存即可;設(shè)置屬性則需要向服務(wù)端發(fā)送申請,由服務(wù)端將屬性鍵值對設(shè)置到共享內(nèi)存。property_set流程:
    Android原生Property移植記錄_服務(wù)端_04

property_get流程:

Android原生Property移植記錄_鍵值_05

使用示例

在使用之前先在后臺執(zhí)行服務(wù)端程序property_service(可放到開機(jī)啟動腳本)。

Android原生Property移植記錄_共享內(nèi)存_06image.png

注:在一次開機(jī)中只允許執(zhí)行一次property_service。若希望在property_service出現(xiàn)異常,手動重新執(zhí)行,需先刪除共享文件"dev/__properties__"。

顯示系統(tǒng)設(shè)置的屬性:Android原生Property移植記錄_客戶端_07

手動設(shè)置屬性:Android原生Property移植記錄_服務(wù)端_08

總結(jié)
  • 本篇主要記錄移植Android Property機(jī)制過程以及對其原理的簡要分析,Property可實現(xiàn)多進(jìn)程之間的數(shù)據(jù)交互功能。
  • Property機(jī)制主要使用了socket、mmap和二叉樹的技巧,學(xué)習(xí)其整體的設(shè)計可為后續(xù)工作開發(fā)增加知識儲備。




最后

用心感悟,認(rèn)真記錄,寫好每一篇文章,分享每一框干貨。愿每一篇文章不負(fù)自己,不負(fù)看客!文章所有實現(xiàn)代碼,均可在后臺發(fā)送關(guān)鍵字獲取。


?猜你喜歡

? ????詳解 | Linux系統(tǒng)是如何實現(xiàn)存儲并讀寫文件的???

? ????C++打怪 之 vector??

??Linux進(jìn)程間通信?信號??


更多文章內(nèi)容包括但不限于C/C++、Linux、開發(fā)常用神器等,可進(jìn)入開源519公眾號聊天界面回復(fù)“文章目錄” 或者 菜單欄選擇“文章目錄”查看。



本文摘自 :https://blog.51cto.com/u

開通會員,享受整站包年服務(wù)立即開通 >