VNDK Derleme Sistemi Desteği

Koleksiyonlar ile düzeninizi koruyun İçeriği tercihlerinize göre kaydedin ve kategorilere ayırın.

Android 8.1 ve sonraki sürümlerde, yapı sistemi yerleşik VNDK desteğine sahiptir. VNDK desteği etkinleştirildiğinde, yapı sistemi modüller arasındaki bağımlılıkları kontrol eder, satıcı modülleri için satıcıya özel bir varyant oluşturur ve bu modülleri otomatik olarak belirlenen dizinlere kurar.

VNDK yapı desteği örneği

Bu örnekte, Android.bp modül tanımı libexample adlı bir kitaplığı tanımlar. vendor_available özelliği, çerçeve modüllerini belirtir ve satıcı modülleri libexample bağlı olabilir:

libexample seller_available:true ve vndk.enabled:true

Şekil 1. VNDK desteği etkinleştirildi

Hem yürütülebilir çerçeve /system/bin/foo hem de satıcı tarafından yürütülebilir /vendor/bin/bar libexample bağlıdır ve libexample özelliklerinde shared_libs sahiptir.

Hem çerçeve modülleri hem de satıcı modülleri tarafından libexample kullanılıyorsa, iki tür libexample oluşturulur. Çekirdek varyant ( libexample 'den sonra adlandırılır) çerçeve modülleri tarafından kullanılır ve satıcı varyantı ( libexample.vendor 'dan sonra adlandırılır) satıcı modülleri tarafından kullanılır. İki değişken farklı dizinlere kurulur:

  • Çekirdek değişken, /system/lib[64]/libexample.so içine kurulur.
  • Satıcı varyantı, vndk.enabled true olduğundan vndk.enabled APEX'e yüklenir.

Daha fazla ayrıntı için bkz. Modül tanımı .

Derleme desteğini yapılandırma

Bir ürün cihazı için tam yapı sistemi desteğini etkinleştirmek için, BoardConfig.mk BOARD_VNDK_VERSION :

BOARD_VNDK_VERSION := current

Bu ayarın genel bir etkisi vardır: BoardConfig.mk içinde tanımlandığında tüm modüller kontrol edilir. Sorunlu bir modülü kara listeye alma veya beyaz listeye alma mekanizması olmadığından, BOARD_VNDK_VERSION eklemeden önce tüm gereksiz bağımlılıkları temizlemelisiniz. Ortam değişkenlerinizde BOARD_VNDK_VERSION ayarlayarak bir modülü test edebilir ve derleyebilirsiniz:

$ BOARD_VNDK_VERSION=current m module_name.vendor

BOARD_VNDK_VERSION etkinleştirildiğinde, birkaç varsayılan genel başlık arama yolu kaldırılır . Bunlar şunları içerir:

  • frameworks/av/include
  • frameworks/native/include
  • frameworks/native/opengl/include
  • hardware/libhardware/include
  • hardware/libhardware_legacy/include
  • hardware/ril/include
  • libnativehelper/include
  • libnativehelper/include_deprecated
  • system/core/include
  • system/media/audio/include

Bir modül bu dizinlerdeki başlıklara bağlıysa, bağımlılıkları (açıkça) header_libs , static_libs ve/veya shared_libs ile belirtmelisiniz.

VNDK APEX

Android 10 ve önceki sürümlerde, vndk.enabled içeren modüller /system/lib[64]/vndk[-sp]-${VER} . Android 11 ve sonraki sürümlerde, VNDK kitaplıkları bir APEX biçiminde paketlenir ve VNDK APEX'in adı com.android.vndk.v${VER} şeklindedir. Cihaz yapılandırmasına bağlı olarak, VNDK APEX düzleştirilmiş veya düzleştirilmemiştir ve kurallı yoldan /apex/com.android.vndk.v${VER /apex/com.android.vndk.v${VER} kullanılabilir.

VNDK APEX

Şekil 2. VNDK APEX

Modül tanımı

BOARD_VNDK_VERSION ile Android oluşturmak için, Android.mk veya Android.bp modül tanımını gözden geçirmelisiniz. Bu bölüm, farklı türde modül tanımlarını, VNDK ile ilgili çeşitli modül özelliklerini ve yapı sisteminde uygulanan bağımlılık denetimlerini açıklar.

Satıcı modülleri

Satıcı modülleri, satıcı bölümüne yüklenmesi gereken satıcıya özel yürütülebilir dosyalar veya paylaşılan kitaplıklardır. Android.bp dosyalarında satıcı modülleri, satıcı veya tescilli özelliği true olarak ayarlamalıdır. Android.mk dosyalarında, satıcı modülleri LOCAL_VENDOR_MODULE veya LOCAL_PROPRIETARY_MODULE true olarak ayarlamalıdır.

BOARD_VNDK_VERSION tanımlanırsa, yapı sistemi satıcı modülleri ile çerçeve modülleri arasındaki bağımlılıklara izin vermez ve şu durumlarda hatalar verir:

  • vendor:true vendor:true bir modüle bağlıdır veya
  • vendor:true olan bir modül, ne vendor:true ne de vendor_available:true olan llndk_library olmayan bir modüle bağlıdır.

Bağımlılık denetimi, Android.bp'de header_libs , static_libs ve LOCAL_SHARED_LIBRARIES için ve shared_libs Android.bp , LOCAL_STATIC_LIBRARIES ve LOCAL_HEADER_LIBRARIES için Android.mk .

LL-NDK

LL-NDK paylaşılan kitaplıkları, kararlı ABI'lere sahip paylaşılan kitaplıklardır. Hem çerçeve hem de satıcı modülleri aynı ve en son uygulamayı paylaşır. Her LL-NDK paylaşılan kitaplığı için Android.bp , bir llndk_library modül tanımı içerir:

llndk_library {
    name: "libvndksupport",
    symbol_file: "libvndksupport.map.txt",
}

Bu modül tanımı, bir modül adını ve satıcı modülleri tarafından görülebilen sembolleri tanımlayan bir sembol dosyasını belirtir. Örneğin:

LIBVNDKSUPPORT {
  global:
    android_load_sphal_library; # llndk
    android_unload_sphal_library; # llndk
  local:
    *;
};

Sembol dosyasına bağlı olarak yapı sistemi, satıcı modülleri için BOARD_VNDK_VERSION etkinleştirildiğinde bu kitaplıklarla bağlantı kuran bir saplama paylaşımlı kitaplık oluşturur. Saplama paylaşılan kitaplığına yalnızca şu durumlarda bir sembol eklenir:

  • Bölüm sonunda _PRIVATE veya _PLATFORM ile tanımlı değil,
  • #platform-only #platform etiketine sahip değildir ve
  • #introduce* etiketleri yok veya etiket hedefle eşleşiyor.

VNDK

Android.bp dosyalarında, cc_library , cc_library_static , cc_library_shared ve cc_library_headers modül tanımları VNDK ile ilgili üç özelliği destekler: vendor_available , vndk.enabled ve vndk.support_system_process .

vendor_available veya vndk.enabled true ise, iki değişken ( temel ve satıcı ) oluşturulabilir. Çekirdek varyant bir çerçeve modülü olarak ele alınmalı ve satıcı varyantı bir satıcı modülü olarak ele alınmalıdır. Bazı çerçeve modülleri bu modüle bağlıysa, çekirdek varyant oluşturulur. Bazı satıcı modülleri bu modüle bağlıysa, satıcı varyantı oluşturulur. Derleme sistemi aşağıdaki bağımlılık kontrollerini zorlar:

  • Çekirdek varyant her zaman yalnızca çerçevedir ve satıcı modüllerine erişilemez.
  • Satıcı varyantı, çerçeve modüllerine her zaman erişilemez.
  • header_libs , static_libs ve/veya shared_libs içinde belirtilen satıcı varyantının tüm bağımlılıkları ya bir llndk_library ya da vendor_available ya da vndk.enabled içeren bir modül olmalıdır.
  • vendor_available true ise, satıcı değişkenine tüm satıcı modülleri tarafından erişilebilir.
  • vendor_available false ise, satıcı değişkenine yalnızca diğer VNDK veya VNDK-SP modülleri tarafından erişilebilir (yani, vendor:true olan modüller, vendor_available:false modüllerini bağlayamaz).

cc_library veya cc_library_shared için varsayılan kurulum yolu aşağıdaki kurallarla belirlenir:

  • Çekirdek varyant /system/lib[64] kurulur.
  • Satıcı varyantı yükleme yolu değişebilir:
    • vndk.enabled false ise, satıcı varyantı /vendor/lib[64] içine kurulur.
    • vndk.enabled true ise, satıcı varyantı VNDK APEX( com.android.vndk.v${VER} ) içine kurulur.

Aşağıdaki tablo, derleme sisteminin satıcı değişkenlerini nasıl ele aldığını özetler:

satıcı_kullanılabilir vndk
etkinleştirilmiş
vndk
support_same_process
Satıcı varyant açıklamaları
true false false Satıcı varyantları SADECE VND'dir . Paylaşılan kitaplıklar /vendor/lib[64] içine kurulur.
true Geçersiz (Derleme hatası)
true false Satıcı varyantları VNDK'dır . Paylaşılan kitaplıklar VNDK APEX'e yüklenir.
true Satıcı varyantları VNDK-SP'dir . Paylaşılan kitaplıklar VNDK APEX'e yüklenir.

false

false

false

Satıcı varyantı yok. Bu modül YALNIZCA FWK'dir .

true Geçersiz (Derleme hatası)
true false Satıcı varyantları VNDK-Private'dir . Paylaşılan kitaplıklar VNDK APEX'e yüklenir. Bunlar doğrudan satıcı modülleri tarafından kullanılmamalıdır.
true Satıcı varyantları VNDK-SP-Private'dir . Paylaşılan kitaplıklar VNDK APEX'e yüklenir. Bunlar doğrudan satıcı modülleri tarafından kullanılmamalıdır.

VNDK uzantıları

VNDK uzantıları, ek API'lere sahip VNDK paylaşımlı kitaplıklardır. Uzantılar /vendor/lib[64]/vndk[-sp] (sürüm son eki olmadan) konumuna yüklenir ve çalışma zamanında orijinal VNDK paylaşılan kitaplıklarını geçersiz kılar.

VNDK uzantılarını tanımlama

Android 9 ve sonraki sürümlerde, Android.bp VNDK uzantılarını yerel olarak destekler. Bir extends uzantısı oluşturmak için, vendor:true ve extensions özelliğiyle başka bir modül tanımlayın:

cc_library {
    name: "libvndk",
    vendor_available: true,
    vndk: {
        enabled: true,
    },
}

cc_library {
    name: "libvndk_ext",
    vendor: true,
    vndk: {
        enabled: true,
        extends: "libvndk",
    },
}

vendor:true , vndk.enabled:true ve extensions özelliklerine sahip bir modül extends uzantısını tanımlar:

  • Genişletme özelliği, temel bir extends paylaşılan kitaplık adı (veya VNDK-SP paylaşılan kitaplık adı) belirtmelidir.
  • VNDK uzantıları (veya VNDK-SP uzantıları), genişledikleri temel modül adlarından sonra adlandırılır. Örneğin, libvndk_ext çıktı ikili dosyası libvndk.so yerine libvndk_ext.so .
  • VNDK uzantıları /vendor/lib[64]/vndk içine kurulur.
  • VNDK-SP uzantıları /vendor/lib[64]/vndk-sp içine kurulur.
  • Temel paylaşılan kitaplıkların hem vndk.enabled:true hem de seller_available: vendor_available:true olması gerekir.

Bir VNDK-SP uzantısı, bir VNDK-SP paylaşılan kitaplığından genişletilmelidir ( vndk.support_system_process eşit olmalıdır):

cc_library {
    name: "libvndk_sp",
    vendor_available: true,
    vndk: {
        enabled: true,
        support_system_process: true,
    },
}

cc_library {
    name: "libvndk_sp_ext",
    vendor: true,
    vndk: {
        enabled: true,
        extends: "libvndk_sp",
        support_system_process: true,
    },
}

VNDK uzantıları (veya VNDK-SP uzantıları), diğer satıcı tarafından paylaşılan kitaplıklara bağlı olabilir:

cc_library {
    name: "libvndk",
    vendor_available: true,
    vndk: {
        enabled: true,
    },
}

cc_library {
    name: "libvndk_ext",
    vendor: true,
    vndk: {
        enabled: true,
        extends: "libvndk",
    },
    shared_libs: [
        "libvendor",
    ],
}

cc_library {
    name: "libvendor",
    vendor: true,
}

VNDK uzantılarını kullanma

Bir satıcı modülü, VNDK uzantıları tarafından tanımlanan ek API'lere bağlıysa, modülün, paylaşılan_libs özelliğinde shared_libs uzantısının adını belirtmesi gerekir:

// A vendor shared library example
cc_library {
    name: "libvendor",
    vendor: true,
    shared_libs: [
        "libvndk_ext",
    ],
}

// A vendor executable example
cc_binary {
    name: "vendor-example",
    vendor: true,
    shared_libs: [
        "libvndk_ext",
    ],
}

Bir satıcı modülü VNDK uzantılarına bağlıysa, bu VNDK uzantıları otomatik olarak /vendor/lib[64]/vndk[-sp] . Bir modül artık bir VNDK uzantısına bağlı değilse, paylaşılan kitaplığı kaldırmak için CleanSpec.mk temiz bir adım ekleyin. Örneğin:

$(call add-clean-step, rm -rf $(TARGET_OUT_VENDOR)/lib/libvndk.so)

koşullu derleme

Bu bölüm, aşağıdaki üç VNDK paylaşılan kitaplığı arasındaki ince farkların (örneğin, varyantlardan birinden bir özellik ekleme veya kaldırma) nasıl ele alınacağını açıklar:

  • Çekirdek varyant (örn /system/lib[64]/libexample.so )
  • Satıcı varyantı (ör /apex/com.android.vndk.v${VER}/lib[64]/libexample.so )
  • VNDK uzantısı (örn /vendor/lib[64]/vndk[-sp]/libexample.so )

Koşullu derleyici bayrakları

Android derleme sistemi, varsayılan olarak satıcı varyantları ve VNDK uzantıları için __ANDROID_VNDK__ tanımlar. Kodu C önişlemci korumalarıyla koruyabilirsiniz:

void all() { }

#if !defined(__ANDROID_VNDK__)
void framework_only() { }
#endif

#if defined(__ANDROID_VNDK__)
void vndk_only() { }
#endif

__ANDROID_VNDK__'ye ek olarak, __ANDROID_VNDK__ farklı cflags veya cppflags Android.bp . target.vendor içinde belirtilen cflags veya cppflags , satıcı varyantına özeldir.

Örneğin, aşağıdaki Android.bp libexample ve libexample_ext tanımlar:

cc_library {
    name: "libexample",
    srcs: ["src/example.c"],
    vendor_available: true,
    vndk: {
        enabled: true,
    },
    target: {
        vendor: {
            cflags: ["-DLIBEXAMPLE_ENABLE_VNDK=1"],
        },
    },
}

cc_library {
    name: "libexample_ext",
    srcs: ["src/example.c"],
    vendor: true,
    vndk: {
        enabled: true,
        extends: "libexample",
    },
    cflags: [
        "-DLIBEXAMPLE_ENABLE_VNDK=1",
        "-DLIBEXAMPLE_ENABLE_VNDK_EXT=1",
    ],
}

Ve bu src/example.c kod listesi:

void all() { }

#if !defined(LIBEXAMPLE_ENABLE_VNDK)
void framework_only() { }
#endif

#if defined(LIBEXAMPLE_ENABLE_VNDK)
void vndk() { }
#endif

#if defined(LIBEXAMPLE_ENABLE_VNDK_EXT)
void vndk_ext() { }
#endif

Bu iki dosyaya göre, yapı sistemi, aşağıdaki dışa aktarılan sembollerle paylaşılan kitaplıklar oluşturur:

Kurulum yolu Dışa aktarılan semboller
/system/lib[64]/libexample.so all , framework_only
/apex/com.android.vndk.v${VER}/lib[64]/libexample.so all , vndk
/vendor/lib[64]/vndk/libexample.so all , vndk , vndk_ext

Dışa aktarılan sembollerle ilgili gereksinimler

VNDK ABI denetleyicisi , VNDK satıcı değişkenlerinin ABI'sini ve VNDK uzantılarını prebuilts prebuilts/abi-dumps/vndk altındaki referans ABI dökümleriyle karşılaştırır.

  • VNDK satıcı varyantları tarafından dışa aktarılan semboller (örn /apex/com.android.vndk.v${VER}/lib[64]/libexample.so ) ABI dökümlerinde tanımlanan sembollerle (bunların üst kümeleri değil) aynı olmalıdır.
  • VNDK uzantıları tarafından dışa aktarılan semboller (örn /vendor/lib[64]/vndk/libexample.so ) ABI dökümlerinde tanımlanan sembollerin üst kümeleri olmalıdır.

VNDK satıcı varyantları veya VNDK uzantıları yukarıdaki gereksinimleri karşılayamazsa, VNDK ABI denetleyicisi derleme hataları yayar ve derlemeyi durdurur.

Satıcı varyantlarından kaynak dosyaları veya paylaşılan kitaplıkları hariç tutma

Kaynak dosyaları satıcı varyantından hariç tutmak için bunları exclude_srcs özelliğine ekleyin. Benzer şekilde, paylaşılan kitaplıkların satıcı varyantıyla bağlantılı olmadığından emin olmak için bu kitaplıkları exclude_shared_libs özelliğine ekleyin. Örneğin:

cc_library {
    name: "libexample_cond_exclude",
    srcs: ["fwk.c", "both.c"],
    shared_libs: ["libfwk_only", "libboth"],
    vendor_available: true,
    target: {
        vendor: {
            exclude_srcs: ["fwk.c"],
            exclude_shared_libs: ["libfwk_only"],
        },
    },
}

Bu örnekte, libexample_cond_exclude öğesinin çekirdek varyantı libexample_cond_exclude ve both.c gelen kodu içerir ve fwk.c ve libfwk_only paylaşılan kitaplıklarına libboth . libexample_cond_exclude satıcı değişkeni, libexample_cond_exclude , exclude_srcs özelliği tarafından hariç fwk.c , yalnızca both.c kodu içerir. Benzer şekilde, yalnızca libfwk_only exclude_shared_libs özelliği tarafından dışlandığı için yalnızca paylaşılan kitaplık libboth bağlıdır.

VNDK uzantılarından başlıkları dışa aktarma

Bir VNDK uzantısı, bir VNDK paylaşılan kitaplığına yeni sınıflar veya yeni işlevler ekleyebilir. Bu bildirimlerin bağımsız başlıklarda tutulması ve mevcut başlıkların değiştirilmesinden kaçınılması önerilir.

Örneğin, VNDK uzantısı libexample_ext için include-ext/example/ext/feature_name.h adlı yeni bir başlık dosyası oluşturulur:

  • Android.bp
  • include-ext/example/ext/özellik_adı.h
  • dahil/örnek/örnek.h
  • kaynak/örnek.c
  • kaynak/dahili/özellik_adı.c

Aşağıdaki Android.bp , libexample dışa aktarmaları yalnızca include , oysa libexample_ext dışa aktarmaları hem include hem de include include-ext ext'tir. Bu, feature_name.h libexample kullanıcıları tarafından yanlışlıkla dahil edilmemesini sağlar:

cc_library {
    name: "libexample",
    srcs: ["src/example.c"],
    export_include_dirs: ["include"],
    vendor_available: true,
    vndk: {
        enabled: true,
    },
}

cc_library {
    name: "libexample_ext",
    srcs: [
        "src/example.c",
        "src/ext/feature_name.c",
    ],
    export_include_dirs: [
        "include",
        "include-ext",
    ],
    vendor: true,
    vndk: {
        enabled: true,
        extends: "libexample",
    },
}

Uzantıları bağımsız başlık dosyalarına ayırmak mümkün değilse, bir alternatif #ifdef korumaları eklemektir. Ancak, tüm VNDK uzantısı kullanıcılarının tanım bayraklarını eklediğinden emin olun. cc_defaults tanımlı bayraklar eklemek ve paylaşılan kitaplıkları cflags ile bağlamak için shared_libs tanımlayabilirsiniz.

Örneğin, VNDK uzantısı libexample2_ext yeni bir üye işlevi Example2::get_b() eklemek için, mevcut başlık dosyasını değiştirmeli ve bir #ifdef koruması eklemelisiniz:

#ifndef LIBEXAMPLE2_EXAMPLE_H_
#define LIBEXAMPLE2_EXAMPLE_H_

class Example2 {
 public:
  Example2();

  void get_a();

#ifdef LIBEXAMPLE2_ENABLE_VNDK_EXT
  void get_b();
#endif

 private:
  void *impl_;
};

#endif  // LIBEXAMPLE2_EXAMPLE_H_

cc_defaults adlı bir libexample2_ext_defaults , libexample2_ext kullanıcıları için tanımlanmıştır:

cc_library {
    name: "libexample2",
    srcs: ["src/example2.cpp"],
    export_include_dirs: ["include"],
    vendor_available: true,
    vndk: {
        enabled: true,
    },
}

cc_library {
    name: "libexample2_ext",
    srcs: ["src/example2.cpp"],
    export_include_dirs: ["include"],
    vendor: true,
    vndk: {
        enabled: true,
        extends: "libexample2",
    },
    cflags: [
        "-DLIBEXAMPLE2_ENABLE_VNDK_EXT=1",
    ],
}

cc_defaults {
    name: "libexample2_ext_defaults",
    shared_libs: [
        "libexample2_ext",
    ],
    cflags: [
        "-DLIBEXAMPLE2_ENABLE_VNDK_EXT=1",
    ],
}

libexample2_ext kullanıcıları, defaults özelliklerine basitçe libexample2_ext_defaults :

cc_binary {
    name: "example2_user_executable",
    defaults: ["libexample2_ext_defaults"],
    vendor: true,
}

Ürün paketleri

Android derleme sisteminde, PRODUCT_PACKAGES değişkeni, aygıta yüklenmesi gereken yürütülebilir dosyaları, paylaşılan kitaplıkları veya paketleri belirtir. Belirtilen modüllerin geçişli bağımlılıkları da örtük olarak cihaza kurulur.

BOARD_VNDK_VERSION etkinleştirilirse, vendor_available veya vndk.enabled olan modüller özel muamele görür. Bir çerçeve modülü, vendor_available veya vndk.enabled olan bir modüle bağlıysa, çekirdek varyant geçişli kurulum setine dahil edilir. Bir satıcı modülü vendor_available olan bir modüle bağlıysa, satıcı varyantı geçişli kurulum kümesine dahil edilir. Ancak, satıcı modülleri tarafından kullanılsın veya kullanılmasın vndk.enabled modüllerin satıcı varyantları yüklenir.

Bağımlılıklar yapı sistemi için görünmez olduğunda (örneğin çalışma zamanında dlopen() ile açılabilen paylaşılan kitaplıklar), bu modülleri açık bir şekilde kurmak için PRODUCT_PACKAGES içindeki modül adlarını belirtmelisiniz.

Bir modülde vendor_available veya vndk.enabled , modül adı çekirdek varyantı anlamına gelir. PRODUCT_PACKAGES içinde satıcı varyantını açıkça belirtmek için modül adına bir .vendor son eki ekleyin. Örneğin:

cc_library {
    name: "libexample",
    srcs: ["example.c"],
    vendor_available: true,
}

Bu örnekte, libexample , /system/lib[64]/libexample.so ve libexample.vendor , /vendor/lib[64]/libexample.so anlamına gelir. /vendor/lib[64]/libexample.so dosyasını yüklemek için /vendor/lib[64]/libexample.so libexample.vendor PRODUCT_PACKAGES öğesine ekleyin:

PRODUCT_PACKAGES += libexample.vendor