VNDK derleme sistemi desteği

Android 8.1 ve sonraki sürümlerde, derleme sisteminde yerleşik VNDK desteği bulunur. Zaman VNDK desteği etkinleştirildiğinde, derleme sistemi tedarikçi modülleri için tedarikçiye özgü bir varyant oluşturur ve bu modülleri belirlenen dizinlere otomatik olarak yükler.

VNDK derleme desteği örneği

Bu örnekte, Android.bp modülü tanımı bir libexample adlı kitaplık. vendor_available özelliği, çerçeve modüllerinin ve tedarikçi modüllerinin libexample:

libexample provider_available:true ve vndk.enabled:true

Şekil 1. Destek etkin.

Hem yürütülebilir /system/bin/foo çerçevesi hem de tedarikçi yürütülebilir /vendor/bin/bar bağımlı libexample ve shared_libs mülklerinde libexample bulunuyor.

libexample hem çerçeve modülleri hem de tedarikçi firma tarafından kullanılıyorsa modüllerinde, libexample ürününün iki varyantı oluşturulmuştur. Temel varyant (libexample ile adlandırılmıştır) çerçeve modülleri ve tedarikçi firma varyantı (libexample.vendor ile adlandırılmıştır) tedarikçi firma tarafından kullanılıyor modüllerinde yer alır. İki varyant farklı dizinlere yüklenir:

  • Çekirdek varyant /system/lib[64]/libexample.so
  • Tedarikçi firma varyantı, VNDK APEX'e yüklenmiştir çünkü vndk.enabled true.

Daha fazla bilgi için Modül tanımı bölümüne bakın.

Derleme desteğini yapılandırma

Bir ürün cihazında tam derleme sistem desteğini etkinleştirmek için BOARD_VNDK_VERSION - BoardConfig.mk:

BOARD_VNDK_VERSION := current

Bu ayarın genel bir etkisi vardır: BoardConfig.mk, tüm modüller işaretlendi. E-posta teslim etmek için rahatsız edici bir modülü kara veya beyaz listeye almak isterseniz, BOARD_VNDK_VERSION eklemeden önce gereksiz bağımlılıklar var. Siz BOARD_VNDK_VERSION parametresini ayarlayarak bir modülü test edebilir ve derleyebilir Ortam değişkenlerinizi ayarlayın:

$ BOARD_VNDK_VERSION=current m module_name.vendor

BOARD_VNDK_VERSION etkinleştirildiğinde bazı varsayılan global ayarlar başlık arama yolları kaldırılır. Bunlardan bazıları:

  • 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 dizinlerin başlıklarına bağımlıysa (açıkça) header_libs, static_libs ve/veya shared_libs.

VNDK APEX

Android 10 ve önceki sürümlerde vndk.enabled içeren modüller şurada yüklendi: /system/lib[64]/vndk[-sp]-${VER}. Android 11 ve sonraki sürümlerde VNDK kitaplıkları APEX biçiminde paketlenir ve VNDK APEX adı com.android.vndk.v${VER} Cihaz yapılandırmasına bağlı olarak, VNDK APEX düzeltilmiş veya düzeltilmemiş olup standart yoldan kullanılabilir /apex/com.android.vndk.v${VER}.

VNDK APEX

Şekil 2. VNDK APEX.

Modül tanımı

Android'i BOARD_VNDK_VERSION ile derlemek için şunu gözden geçirmeniz gerekir: Android.mk veya Android.bp. Bu bölümde farklı modül türleri açıklanmaktadır tanımlar, VNDK ile ilgili çeşitli modül özellikleri ve bağımlılık kontrolleri uygulanmıştır.

Satıcı modülleri

Tedarikçi firma modülleri, tedarikçiye özel yürütülebilir dosyalar veya paylaşılan kitaplıklardır. bir tedarikçi firma bölümüne yüklenmelidir. Android.bp dosyada, tedarikçi firma modülleri, tedarikçi firmayı veya özel mülkü true olarak ayarlamalıdır. Android.mk dosyada tedarikçi modüllerinin ayarlanması gerekiyor LOCAL_VENDOR_MODULE veya LOCAL_PROPRIETARY_MODULE - true.

BOARD_VNDK_VERSION tanımlanırsa derleme sistemi şunlara izin vermez: aşağıdaki durumlarda tedarikçi modülleri ile çerçeve modülleri arasındaki bağımlılıkları gösterir ve hata verir:

  • vendor:true içermeyen bir modül, vendor:true veya
  • vendor:true içeren modüller şuna bağlıdır: hiçbiri içermeyen llndk_library olmayan modül vendor:true veya vendor_available:true.

Bağımlılık kontrolü header_libs, static_libs ve shared_libs inç Android.bp ve LOCAL_HEADER_LIBRARIES adlı kullanıcılara, LOCAL_STATIC_LIBRARIES ve LOCAL_SHARED_LIBRARIES inç Android.mk.

LL-NDK

LL-NDK paylaşılan kitaplıkları, kararlı ABI'lere sahip paylaşılan kitaplıklardır. Her iki çerçeve Satıcı modüllerinde aynı ve en son uygulama ortaktır. Her bir LL-NDK paylaşılan kitaplığı, cc_library bir içerir Sembol dosyasına sahip llndk özelliği:

cc_library {
    name: "libvndksupport",
    llndk: {
        symbol_file: "libvndksupport.map.txt",
    },
}

Sembol dosyası, tedarikçi modüllerinde görünen sembolleri açıklar. Örnek:

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

Derleme sistemi, simge dosyasına göre bağlantı sağlayan tedarikçi firma modülleridir. BOARD_VNDK_VERSION etkinleştirildi. Sapta sembol yer alıyor paylaşılan kitaplığın kullanılması için:

  • Bölüm sonunda _PRIVATE ile tanımlanmamışsa veya _PLATFORM,
  • #platform-only etiketi içermiyor ve
  • #introduce* etiketi içermiyor veya etiket hedefi belirleyebilirsiniz.
ziyaret edin.

VNDK

Android.bp dosyada, cc_library, cc_library_static, cc_library_shared ve cc_library_headers modül tanımları, VNDK ile ilgili üçünü destekliyor mülkler: vendor_available, vndk.enabled ve vndk.support_system_process.

vendor_available veya vndk.enabled true, iki varyant (temel ve sağlayıcı) olabilir geliştirmenizi sağlar. Temel varyant bir çerçeve modülü ve satıcı olarak değerlendirilmelidir. varyantının satıcı modülü olarak işlenmesi gerekir. Bazı çerçeve modülleri, temel varyant oluşturulmuştur. Bazı tedarikçi modüllerinde tedarikçi varyantı oluşturulur. Derleme sistemi aşağıda belirtilen bağımlılık kontrollerini içerir:

  • Temel varyant her zaman yalnızca çerçeve düzeyindedir ve tedarikçi firma tarafından erişilemez. modüllerinde yer alır.
  • Çerçeve modüllerinde tedarikçi varyantına hiçbir zaman erişilemez.
  • Tedarikçi firma varyantının aşağıdaki kriterlerde belirtilen tüm bağımlılıkları header_libs, static_libs ve/veya shared_libs, llndk_library veya bir olmalıdır vendor_available veya vndk.enabled ile entegre edin.
  • vendor_available değeri true ise tedarikçi firma varyantı tüm tedarikçi modüllerine erişilebilir.
  • vendor_available değeri false ise tedarikçi firma varyantı yalnızca diğer VNDK veya VNDK-SP modüllerinde (ör. vendor:true, vendor_available:false bağlantısını bağlayamıyor modüllerinde) yer alır.

cc_library veya cc_library_shared aşağıdaki kurallara göre belirlenir:

  • Temel varyant /system/lib[64] sürümüne yüklendi.
  • Tedarikçi firma varyantının yükleme yolu değişiklik gösterebilir:
    • vndk.enabled değeri false ise tedarikçi firma varyantı /vendor/lib[64] klasörüne yüklendi.
    • vndk.enabled değeri true ise tedarikçi firma varyantı VNDK APEX'e(com.android.vndk.v${VER}) yüklenmiştir.

Aşağıdaki tabloda, derleme sisteminin tedarikçi firma varyantlarını nasıl işlediği özetlenmiştir:

tedarikçi_kullanılabilir vndk
etkin
vndk
destek_aynı_süreç
Satıcı varyantı açıklamaları
true false false Tedarikçi firma varyantları SADECE VND'dir. Paylaşılan kitaplıklar /vendor/lib[64] klasörüne yüklendi.
true Geçersiz (Derleme hatası)
true false Tedarikçi firma varyantları VNDK'dır. Paylaşılan kitaplıklar yüklendi VNDK APEX'e gönderilir.
true Tedarikçi firma varyantları VNDK-SP'dir. Paylaşılan kitaplıklar VNDK APEX'e yüklenmiştir.

false

false

false

Satıcı varyantı yok. Bu modül SADECE FWK biçimindedir.

true Geçersiz (Derleme hatası)
true false Tedarikçi firma varyantları VNDK-Private'dır. Paylaşılan kitaplıklar VNDK APEX'e yüklenmiştir. Bunlar, doğrudan tedarikçi tarafından kullanılır.
true Tedarikçi firma varyantları VNDK-SP-Private'dır. Paylaşılan kitaplıklar VNDK APEX'e yüklenmiştir. Bunlar, doğrudan tedarikçi tarafından kullanılır.

VNDK uzantıları

VNDK uzantıları, ek API'ler içeren VNDK paylaşılan kitaplıklarıdır. Uzantılar /vendor/lib[64]/vndk[-sp] hedefine yüklendi (sürüm son eki olmadan) ve çalışma zamanında orijinal VNDK paylaşılan kitaplıkları geçersiz kılın.

VNDK uzantılarını tanımlama

Android.bp, Android 9 ve sonraki sürümlerde VNDK'yı yerel olarak destekler. uzantılar. Bir VNDK uzantısı oluşturmak için, vendor:true ve extends mülkü:

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 extends özellikleri VNDK uzantısını tanımlar:

  • extends mülkü, temel VNDK paylaşılan bir kitaplık belirtmelidir ad (veya VNDK-SP paylaşılan kitaplık adı).
  • VNDK uzantıları (veya VNDK-SP uzantıları) temel modülün adını alır yer alır. Örneğin, libvndk_ext yerine libvndk.so libvndk_ext.so.
  • VNDK uzantıları, /vendor/lib[64]/vndk klasörüne yüklenir.
  • VNDK-SP uzantıları /vendor/lib[64]/vndk-sp
  • Temel paylaşılan kitaplıklarda her ikisi de vndk.enabled:true olmalıdır ve vendor_available:true.

VNDK-SP uzantıları, VNDK-SP paylaşılan kitaplıkları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ı) paylaşılan diğer tedarikçi firmaya bağlı olabilir kitaplıklar:

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

Tedarikçi firma modülü, VNDK uzantıları tarafından tanımlanan ek API'lere bağlıysa modülü, shared_libs mülk:

// 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",
    ],
}

Tedarikçi firma modülü VNDK uzantılarına bağlıysa bu VNDK uzantıları /vendor/lib[64]/vndk[-sp] hedefine otomatik olarak yüklendi. Bir modül artık bir VNDK uzantısına bağlı değilse Paylaşılan kitaplığı kaldırmak için CleanSpec.mk tuşlarına basın. Örnek:

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

Koşullu derleme

Bu bölümde, küçük farklılıkları (ör. varyantlardan birinde özellik ekleme veya kaldırma). üç VNDK paylaşılan kitaplık:

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

Koşullu derleyici işaretleri

Android derleme sistemi, satıcı için __ANDROID_VNDK__ öğesini tanımlar varyantları ve VNDK uzantıları varsayılan olarak ayarlıdır. Kodu korumaya alabilirsiniz C ön işlemci korumalarıyla test edin:

void all() { }

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

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

__ANDROID_VNDK__ öğesine ek olarak farklı cflags veya Android.bp içinde cppflags belirtilebilir. İlgili içeriği oluşturmak için kullanılan cflags veya cppflags belirtilmiş target.vendor, satıcı varyantına özeldir.

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

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",
    ],
}

src/example.c için de kod listesi şöyle:

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, derleme sistemi paylaşılan kitaplıklar oluşturur şu dışa aktarılan simgelerle:

Kurulum yolu Dışa aktarılan simgeler
/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 simgelerle ilgili koşullar

VNDK ABI denetleyicisi VNDK tedarikçi varyantlarının ABI'sını karşılaştırır ve Referans ABI dökümlerinin altındaki VNDK uzantıları prebuilts/abi-dumps/vndk.

  • VNDK tedarikçi firması varyantları tarafından dışa aktarılan semboller (ör. /apex/com.android.vndk.v${VER}/lib[64]/libexample.so) aynı olmalıdır (üst kümelerine değil) doğru gönderin.
  • VNDK uzantıları tarafından dışa aktarılan simgeler (ör. /vendor/lib[64]/vndk/libexample.so), ABI dökümlerinde tanımlanan semboller.

VNDK tedarikçi firma varyantları veya VNDK uzantıları aşağıdaki adımları takip edemezse yerine getirmek için, VNDK ABI denetleyicisi yapı hataları yayınlar ve seçeceğiz.

Kaynak dosyaları veya paylaşılan kitaplıkları tedarikçi firma varyantlarından hariç tutun

Kaynak dosyaları tedarikçi firma varyantından hariç tutmak için bunları exclude_srcs mülk. Benzer şekilde, paylaşılan kitaplıkların satıcı varyantıyla bağlantılı değilse bu kitaplıkları exclude_shared_libs mülk. Örnek:

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 temel varyantı fwk.c ve both.c kodlarını içerir ve libfwk_only ve libboth adlı paylaşılan kitaplıklarda. İlgili içeriği oluşturmak için kullanılan libexample_cond_exclude ürününün satıcı varyantı yalnızca kodu içeriyor both.c için fwk.c exclude_srcs mülkü. Benzer şekilde, bu yalnızca paylaşılan kitaplığın libboth çünkü libfwk_only exclude_shared_libs mülkü.

VNDK uzantılarından üstbilgileri dışa aktarma

VNDK uzantısı, paylaşılan bir VNDK'ya yeni sınıflar veya yeni işlevler ekleyebilir kitaplığını açar. Bu beyanları bağımsız başlıklarda tutmanız önerilir ve mevcut başlıkları değiştirmeyin.

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

  • Android.bp
  • dahil et-uzantısı/örnek/uzantı/özellik_adı.h
  • içerir/ornek/ornek.h
  • Src/ornek.c
  • src/uzantı/özellik_adı.c

Aşağıdaki Android.bp içinde libexample dışa aktarma yalnızca include, libexample_ext her ikisini de dışa aktarır include ve include-ext. Bu sayede feature_name.h, kullanıcıları tarafından yanlışlıkla dahil edilmeyecek libexample:

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 uygun değilse alternatif olarak #ifdef gard eklemektir. Ancak lütfen VNDK uzantısı kullanıcıları, tanımlama işaretlerini ekler. Bir projenin cflags öğesine tanımlama işaretleri eklemek ve bağlantıyı bağlamak için cc_defaults shared_libs ile paylaşılan kitaplıklar.

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

#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_

libexample2_ext_defaults adlı bir cc_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ı şunları ekleyebilir: defaults içindeki libexample2_ext_defaults mülk:

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

Ürün paketleri

Android derleme sisteminde PRODUCT_PACKAGES değişkeni yürütülebilir dosyaları, paylaşılan kitaplıkları veya yüklü olduğundan emin olun. Belirtilen modüllerin de örtülü olarak cihaza yüklenmiş olması gerekir.

BOARD_VNDK_VERSION etkinleştirilirse vendor_available veya vndk.enabled özel indirim ele alacağız. Çerçeve modülü, vendor_available veya vndk.enabled, temel varyant geçişli yükleme grubuna dahildir. Tedarikçi modülü vendor_available içeren modüle bağlı olarak, tedarikçi firma varyantı geçişli yükleme setine dahildir. Ancak modüllerin tedarikçi firma varyantları vndk.enabled ile yüklü olması gerekir.

Bağımlılıklar derleme sistemi tarafından görülemediğinde (ör. paylaşılan kitaplıklar) (çalışma zamanında dlopen() ile açılabilir) kullanıyorsanız bu modülleri yüklemek için PRODUCT_PACKAGES konumundaki modül adlarını açık bir şekilde belirtmelisiniz.

Bir modülde vendor_available veya vndk.enabled varsa modül adı, temel varyantı anlamına gelir. PRODUCT_PACKAGES içindeki tedarikçi firma varyantına .vendor ekleyin sonekini modül adına ekleyin. Örnek:

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

Bu örnekte libexample, anlamına gelir. /system/lib[64]/libexample.so libexample.vendor /vendor/lib[64]/libexample.so anlamına gelir. Yüklemek için /vendor/lib[64]/libexample.so, libexample.vendor ekleyin kime: PRODUCT_PACKAGES

PRODUCT_PACKAGES += libexample.vendor