アンドロイドHAL層フレーム解析(II)

2つのアンドロイドHAL層構造の前の私達のhw_module_tの主要メンバーの分析(ハードウェアモジュール)とhw_device_t(ハードウェア)、最終的には特定のトップアプリで見てみましょう、運用、ハードウェアを実現する方法ですか?

我々はいくつかのハードウェアメーカーは、独自のコアコードの一部をオープンにしたくないことを知っているので、これらのコードは、HAL層に、それはそれを開かないことを確実にする方法?HAL層コード誰もがそれをダウンロードして知らせてもいないのですか?実際には、ハードウェアの製造元HALコアコード、共有ライブラリ、必要な都度の形態であり、Halは自動的に関連するコールに共有ライブラリをロードします。だから、どのように共有ライブラリに対応するハードウェアの負荷を見つけることですか?我々はこれを言わなければならない理由です。

HALによってアプリ上部捕捉ハードウェアモジュール関数呼び出しhw_get_module JNI層は、HALこの関数は、上部入口を扱っています。だから私たちはここに、この関数は、最初の関数は、HAL層と呼ばれている、プログラムの呼び出しのソースコードを見て処理を実行した場合、我々は来ます

この機能の当初から、プログラムのプロセスの実行には、一緒に行きます。

hw_get_module機能が/hardware/libhardware/hardware.cで定義されている、あなたが見ることができるファイルを開く、次のように定義されています。

 1 int hw_get_module(const char *id, const struct hw_module_t **module) 
 2 {
 3     int status;
 4     int i;
 5     const struct hw_module_t *hmi = NULL;
 6     char prop[PATH_MAX];
 7     char path[PATH_MAX];
 8 
 9     /*
10      * Here we rely on the fact that calling dlopen multiple times on
11      * the same .so will simply increment a refcount (and not load
12      * a new copy of the library).
13      * We also assume that dlopen() is thread-safe.
14      */
15 
16     /* Loop through the configuration variants looking for a module */
17     for (i=0 ; i<HAL_VARIANT_KEYS_COUNT+1 ; i++) {
18         if (i < HAL_VARIANT_KEYS_COUNT) {
19             if (property_get(variant_keys[i], prop, NULL) == 0) {//获取属性
20                 continue;
21             }
22             snprintf(path, sizeof(path), "%s/%s.%s.so",
23                     HAL_LIBRARY_PATH1, id, prop);
24             if (access(path, R_OK) == 0) break;//检查system路径是否有库文件
25 
26             snprintf(path, sizeof(path), "%s/%s.%s.so",
27                      HAL_LIBRARY_PATH2, id, prop);
28             if (access(path, R_OK) == 0) break;//检查vender路径是否有库文件
29         } else {
30             snprintf(path, sizeof(path), "%s/%s.default.so",//如果都没有,则使用缺省的
31                      HAL_LIBRARY_PATH1, id);
32             if (access(path, R_OK) == 0) break;
33         }
34     }
35 
36     status = -ENOENT;
37     if (i < HAL_VARIANT_KEYS_COUNT+1) {
38         /* load the module, if this fails, we're doomed, and we should not try
39          * to load a different variant. */
40         status = load(id, path, module);//装载库,得到module
41     }
42 
43     return status;
44 }

 

 我々は二つのパラメータがあることを知っている最初の行を見て、最初のパラメータは、ハードウェアモジュールを取得するためのID番号である、第2のモジュールのパラメータは、ハードウェアモジュール構造をしたいのポインタです。

このIDに従ってIDと、対応するハードウェアモジュール構造と一致見つけるために、第1のハードウェアモジュールを取得するID HAL上層ニーズ、hw_get_module機能を見ることができます。

検索方法で見てみましょう。

ループのための17本のラインがありますが、上限はHAL_VARIANT_KEYS_COUNT + 1が、それは何このHAL_VARIANT_KEYS_COUNTているのですか?ビューの下に同一のファイルは、以下のとおりです。

static const int HAL_VARIANT_KEYS_COUNT =  (sizeof(variant_keys)/sizeof(variant_keys[0]));

これはariant_keysの配列の要素の元の数です。だから、この配列は、それは何ですか?探して、この文書では、我々は以下のとおりです。

/**
 * There are a set of variant filename for modules. The form of the filename
 * is "<MODULE_ID>.variant.so" so for the led module the Dream variants 
 * of base "ro.product.board", "ro.board.platform" and "ro.arch" would be:
 *
 * led.trout.so
 * led.msm7k.so
 * led.ARMV6.so
 * led.default.so
 */

static const char *variant_keys[] = {
    "ro.hardware",  /* This goes first so that it can pick up a different
                       file on the emulator. */
    "ro.product.board",
    "ro.board.platform",
    "ro.arch"
};

私たちは、それが実際に文字列の配列であることがわかります。駅には何をすべきかを知りません。Hw_get_module機能は、実際には、ライン22を参照してください、forループの中に探し続け、それはHAL_LIBRARY_PATH1は、idは、3つの文字列がパスの外に一緒に入れ小道具です、

次のようにHAL_LIBRARY_PATH1が定義されています。

/** Base path of the hal modules */
#define HAL_LIBRARY_PATH1 "/system/lib/hw"
#define HAL_LIBRARY_PATH2 "/vendor/lib/hw"

idは、この変数の上部に設けられ、支柱値を取得するフロントライン19 property_get(variant_keys [i]は、支柱、NULL)関数である、実際には、この関数は、バリアント名システム相当にariant_keysアレイルックアップによって特性です。値の小道具を取得するための異なるプラットフォームは同じではありません。

取得した値が必要でLEDを取得することプロプTOUT、IDハードウェアモジュールである場合、最後のパスは/system/lib/hw/leds.tout.soからなる文字列です。

ラインアクセスの背後にある24は、それBREAK場合はループの外に、このパスが存在するかどうかを確認することです。ない場合は、下記行くし続けます、

ここでは、わずか数行と同様のフォームを参照することができます

snprintf(path, sizeof(path), "%s/%s.%s.so",  HAL_LIBRARY_PATH2, id, prop);

if (access(path, R_OK) == 0) break;//检查vender路径是否有库文件

結合のHAL_LIBRARY_PATH2「/ベンダー/ LIB / HW」、同じ値を仮定すると、支柱TOUT、ID値がパススペル/ベンダー/ LIB / HW / LEDのうちで、この場合には、ハードウェア・モジュールのLEDで取得する必要が取得されます.tout.so、そのファイルが存在するかどうかを決定します。ループの外に存在する場合。

上記の分析から、実際には、これは我々が二つのことを得ることができ、そこから道検索HAL層の動的共有ライブラリを、次のとおりです。

1.動的共有ライブラリは、典型的には、「/システム/ LIB / HW」と「/ベンダー/ LIB / HW」二つの経路に入れました。

2.「id.variant.so」idはバリアントに上部、ミドルネーム変異体のために提供される場合、名前の形式で動的ライブラリの名前は、プラットフォームの変更に含まれます。

その後、29-32行から我々は、すべての名前の変異体が存在するとき、ルックアップ、パッケージ名の「id.default.so」フォームに関しては、パケットの形で存在していないことがわかります。

ライン37、iが少ないライン38の負荷(ID、パス、モジュール)を、対応するライブラリを見つけ、次にアレイのVAR名を超える場合、(I <HAL_VARIANT_KEYS_COUNT + 1)の場合; //ロード・ライブラリ、取得モジュール。


検索ベースの数字を除外するために、その上ハル層。
 

次は、共有ライブラリがロードされているかを確認するために、ロード関数を入力します。

公開された407元の記事 ウォンの賞賛150 ビュー380 000 +

おすすめ

転載: blog.csdn.net/ds1130071727/article/details/104908801