Bu sayfa, sürücü ve çerçeve arasında işlenen arabelleklerini verimli bir şekilde iletmek için kullanılan veri yapılarını ve yöntemlerini açıklar.
Model derleme zamanında, çerçeve sürücüye sabit işlenenlerin değerlerini sağlar. Sabit işlenenin ömrüne bağlı olarak, değerleri bir HIDL vektöründe veya paylaşılan bir bellek havuzunda bulunur.
- Ömür
CONSTANT_COPY
ise, değerler model yapısınınoperandValues
alanında bulunur. HIDL vektöründeki değerler işlemler arası iletişim (IPC) sırasında kopyalandığından, bu genellikle yalnızca skaler işlenenler (örneğin,ADD
aktivasyon skaleri) ve küçük tensör parametreleri (örneğin,RESHAPE
içindeki şekil tensörü). - Ömür
CONSTANT_REFERENCE
ise, değerler model yapısınınpools
alanında bulunur. IPC sırasında ham değerleri kopyalamak yerine yalnızca paylaşılan bellek havuzlarının tutamaçları çoğaltılır. Bu nedenle, paylaşılan bellek havuzlarını kullanarak büyük miktarda veriyi (örneğin, evrişimlerdeki ağırlık parametreleri) tutmak HIDL vektörlerinden daha verimlidir.
Model yürütme zamanında, çerçeve sürücüye giriş ve çıkış işlenenlerinin arabelleklerini sağlar. Bir HIDL vektöründe gönderilebilecek derleme zamanı sabitlerinin aksine, bir yürütmenin giriş ve çıkış verileri her zaman bir bellek havuzları topluluğu aracılığıyla iletilir.
HIDL veri türü hidl_memory
, eşlenmemiş bir paylaşılan bellek havuzunu temsil etmek için hem derlemede hem de yürütmede kullanılır. Sürücü, belleği hidl_memory
veri türünün adına göre kullanılabilir hale getirmek için buna göre eşlemelidir. Desteklenen bellek adları şunlardır:
-
ashmem
: Android paylaşımlı hafıza. Daha fazla ayrıntı için bkz. bellek . -
mmap_fd
:mmap
aracılığıyla bir dosya tanıtıcı tarafından desteklenen paylaşılan bellek. -
hardware_buffer_blob
: AHARDWARE_BUFFER_FORMAT_BLOB biçiminde birAHARDWARE_BUFFER_FORMAT_BLOB
tarafından desteklenen paylaşılan bellek. Sinir Ağları (NN) HAL 1.2'den edinilebilir. Daha fazla ayrıntı için bkz. AHardwareBuffer . -
hardware_buffer
:AHARDWARE_BUFFER_FORMAT_BLOB
biçimini kullanmayan genel bir AHardwareBuffer tarafından desteklenen paylaşılan bellek. BLOB olmayan mod donanım arabelleği yalnızca model yürütmede desteklenir. NN HAL 1.2'den edinilebilir. Daha fazla ayrıntı için bkz. AHardwareBuffer .
NN HAL 1.3'ten itibaren NNAPI, sürücü tarafından yönetilen arabellekler için ayırıcı arabirimleri sağlayan bellek etki alanlarını destekler. Sürücü tarafından yönetilen arabellekler, yürütme girdileri veya çıktıları olarak da kullanılabilir. Daha fazla ayrıntı için bkz. Bellek etki alanları .
NNAPI sürücüleri, ashmem
ve mmap_fd
bellek adlarının eşlenmesini desteklemelidir. NN HAL 1.3'ten itibaren, sürücülerin hardware_buffer_blob
eşlemesini de desteklemesi gerekir. Genel BLOB olmayan mod hardware_buffer
ve bellek etki alanları için destek isteğe bağlıdır.
AHdonanım Tamponu
AHardwareBuffer, Gralloc arabelleğini saran bir paylaşılan bellek türüdür. Android 10'da, Neural Networks API (NNAPI), AHardwareBuffer kullanımını destekleyerek, sürücünün verileri kopyalamadan yürütme gerçekleştirmesine olanak tanır, bu da uygulamalar için performansı ve güç tüketimini artırır. Örneğin, bir kamera HAL yığını, kamera NDK ve medya NDK API'leri tarafından oluşturulan AHardwareBuffer tutamaçlarını kullanarak makine öğrenimi iş yükleri için AHardwareBuffer nesnelerini NNAPI'ye iletebilir. Daha fazla bilgi için bkz. ANeuralNetworksMemory_createFromAHardwareBuffer
.
NNAPI'de kullanılan AHardwareBuffer nesneleri, hardware_buffer
veya hardware_buffer_blob
adlı bir hidl_memory
yapısı aracılığıyla sürücüye geçirilir. hidl_memory
struct hardware_buffer_blob
, yalnızca AHARDWAREBUFFER_FORMAT_BLOB
biçimine sahip AHardwareBuffer nesnelerini temsil eder.
Çerçevenin gerektirdiği bilgiler, hidl_memory
yapısının hidl_handle
alanında kodlanmıştır. hidl_handle
alanı, AHardwareBuffer veya Gralloc arabelleği hakkında gerekli tüm meta verileri kodlayan native_handle
öğesini sarar.
Sürücü, sağlanan hidl_handle
alanının kodunu düzgün bir şekilde çözmeli ve hidl_handle
tarafından açıklanan belleğe erişmelidir. getSupportedOperations_1_2
, getSupportedOperations_1_1
veya getSupportedOperations
yöntemi çağrıldığında, sürücü sağlanan hidl_handle
kodunu çözüp çözemeyeceğini ve hidl_handle
tarafından açıklanan belleğe erişip erişemeyeceğini algılamalıdır. Sabit bir işlenen için kullanılan hidl_handle
alanı desteklenmiyorsa model hazırlama başarısız olmalıdır. Yürütmenin bir giriş veya çıkış işleneni için kullanılan hidl_handle
alanı desteklenmiyorsa yürütme başarısız olmalıdır. Model hazırlama veya yürütme başarısız olursa sürücünün bir GENERAL_FAILURE
hata kodu döndürmesi önerilir.
Bellek alanları
Android 11 veya sonraki sürümleri çalıştıran aygıtlar için NNAPI, sürücü tarafından yönetilen arabellekler için ayırıcı arabirimleri sağlayan bellek etki alanlarını destekler. Bu, aynı sürücü üzerinde ardışık yürütmeler arasında gereksiz veri kopyalamayı ve dönüştürmeyi önleyerek, aygıt yerel belleklerinin yürütmeler arasında geçirilmesine olanak tanır. Bu akış Şekil 1'de gösterilmektedir.
Şekil 1. Bellek etki alanlarını kullanan arabellek veri akışı
Bellek etki alanı özelliği, çoğunlukla sürücüye dahil olan ve istemci tarafında sık erişime ihtiyaç duymayan tensörler için tasarlanmıştır. Bu tür tensörlerin örnekleri, dizi modellerindeki durum tensörlerini içerir. İstemci tarafında sık CPU erişimine ihtiyaç duyan tensörler için paylaşılan bellek havuzlarının kullanılması tercih edilir.
Bellek etki alanı özelliğini desteklemek için, çerçevenin sürücü tarafından yönetilen arabellek ayırma talebinde bulunmasına izin vermek için IDevice::allocate
uygulayın. Tahsis sırasında çerçeve, arabellek için aşağıdaki özellikleri ve kullanım kalıplarını sağlar:
-
BufferDesc
, arabelleğin gerekli özelliklerini açıklar. -
BufferRole
, arabelleğin potansiyel kullanım modelini hazırlanmış bir modelin girdisi veya çıktısı olarak tanımlar. Arabellek ayırma sırasında birden çok rol belirtilebilir ve ayrılan arabellek yalnızca belirtilen roller olarak kullanılabilir.
Tahsis edilen arabellek sürücüde dahilidir. Bir sürücü herhangi bir arabellek konumu veya veri düzeni seçebilir. Arabellek başarıyla tahsis edildiğinde, sürücünün istemcisi, döndürülen belirteci veya IBuffer
nesnesini kullanarak arabelleğe başvurabilir veya onunla etkileşim kurabilir.
IDevice::allocate
öğesi, bir yürütmenin Request
yapısındaki MemoryPool
nesnelerinden biri olarak arabelleğe başvururken sağlanır. Bir işlemin başka bir işlemde tahsis edilen arabelleğe erişmeye çalışmasını önlemek için, sürücünün arabelleğin her kullanımında uygun doğrulama uygulaması gerekir. Sürücü, arabellek kullanımının ayırma sırasında sağlanan BufferRole
rollerinden biri olduğunu doğrulamalı ve kullanım yasa dışıysa yürütmeyi hemen başarısızlığa uğratmalıdır.
IBuffer
nesnesi, açık bellek kopyalama için kullanılır. Belirli durumlarda, sürücünün istemcisi, paylaşılan bir bellek havuzundan sürücü tarafından yönetilen arabelleği başlatmalı veya arabelleği paylaşılan bir bellek havuzuna kopyalamalıdır. Örnek kullanım durumları şunları içerir:
- Durum tensörünün başlatılması
- Ara sonuçları önbelleğe alma
- CPU'da geri dönüş yürütme
Bu kullanım durumlarını desteklemek için sürücü, bellek etki alanı ayırmayı destekliyorsa, mmap_fd
, mmap_fd ve hardware_buffer_blob
ile ashmem
IBuffer::copyTo
ve IBuffer::copyFrom
uygulamalıdır. Sürücünün BLOB olmayan modu hardware_buffer
desteklemesi isteğe bağlıdır.
Tampon tahsisi sırasında, tamponun boyutları, BufferRole
BufferDesc
sağlanan boyutlardan çıkarılabilir. Tüm boyutsal bilgiler bir araya geldiğinde, arabellek bilinmeyen boyutlara veya dereceye sahip olabilir. Böyle bir durumda tampon, model girdisi olarak kullanıldığında boyutların sabitlendiği esnek bir durumda ve model çıktısı olarak kullanıldığında ise dinamik bir durumdadır. Aynı arabellek, farklı yürütmelerde farklı şekillerde çıktılarla kullanılabilir ve sürücü, arabellek yeniden boyutlandırmasını düzgün bir şekilde işlemelidir.
Bellek alanı isteğe bağlı bir özelliktir. Bir sürücü, çeşitli nedenlerle belirli bir tahsis talebini destekleyemediğini belirleyebilir. Örneğin:
- İstenen arabellek dinamik bir boyuta sahip.
- Sürücünün, büyük arabellekleri işlemesini engelleyen bellek kısıtlamaları vardır.
Sürücü tarafından yönetilen arabellekten aynı anda birkaç farklı iş parçacığının okunması mümkündür. Yazma veya okuma/yazma için arabelleğe aynı anda erişim tanımlanmamıştır, ancak sürücü hizmetini çökertmemeli veya arayanı süresiz olarak engellememelidir. Sürücü bir hata döndürebilir veya arabelleğin içeriğini belirsiz bir durumda bırakabilir.