Corresponder às regras

Os dois pares de matrizes e manifestos de compatibilidade precisam ser conciliados para verificar se o framework e a implementação do fornecedor podem funcionar um com o outro. Essa verificação é bem-sucedida após uma correspondência entre a matriz de compatibilidade do framework e o manifesto do dispositivo, bem como entre o manifesto do framework e a matriz de compatibilidade do dispositivo.

Essa verificação é feita no momento do build, no momento da geração do pacote de atualização OTA, no momento da inicialização e nos testes de compatibilidade do VTS.

As seções a seguir detalham as regras de correspondência usadas por vários componentes.

Correspondências de versão da matriz de compatibilidade do framework

Para corresponder um manifesto de dispositivo a uma matriz de compatibilidade do framework, a versão do FCM de envio especificada por manifest.target-level precisa ser exatamente igual à versão do FCM especificada por compatibility-matrix.level. Caso contrário, não há correspondência.

Quando a matriz de compatibilidade do framework é solicitada com libvintf, essa correspondência é sempre bem-sucedida porque libvintf abre o manifesto do dispositivo, recupera a versão do FCM de envio e retorna a matriz de compatibilidade do framework nessa versão do FCM de envio (mais algumas HALs opcionais de matrizes de compatibilidade em versões mais recentes do FCM).

Correspondências do HAL

A regra HAL-match identifica as versões dos elementos hal em um arquivo de manifesto que são consideradas compatíveis com o proprietário da matriz de compatibilidade correspondente.

HIDL e HALs nativos

As regras de correspondência para HIDL e HALs nativos são as seguintes.

  • Vários elementos <hal> são avaliados com uma única relação AND.
  • Os elementos <hal> podem ter <hal optional="true"> para marcá-los como não obrigatórios. Aviso: esse optional não é mais compatível com o Android 15
  • Vários elementos <version> no mesmo <hal> têm a relação OR. Se duas ou mais versões forem especificadas, apenas uma delas precisa ser implementada. Confira o exemplo de DRM abaixo.
  • Vários elementos <instance> e <regex-instance> no mesmo <hal> são avaliados com uma única relação AND quando o <hal> é necessário. Consulte o <ahref="#drm">exemplo de DRM abaixo</ahref="#drm">.

Exemplo: correspondência bem-sucedida do HAL para um módulo

Para uma HAL na versão 2.5, a regra de correspondência é a seguinte:

Matriz Manifesto correspondente
2.5 2.5-2.∞. Na matriz de compatibilidade, 2.5 é a abreviação de 2.5-5.
2.5-7 2,5-2,∞. Indica o seguinte:
  • A 2.5 é a versão mínima necessária. Isso significa que um manifesto que fornece o HAL 2.0-2.4 não é compatível.
  • 2.7 é a versão máxima que pode ser solicitada. Isso significa que o proprietário da matriz de compatibilidade (framework ou dispositivo) não vai solicitar versões além da 2.7. O proprietário do manifesto correspondente ainda pode veicular a versão 2.10 (como exemplo) quando a 2.7 for solicitada. O proprietário da matriz de compatibilidade sabe apenas que o serviço solicitado é compatível com a versão 2.7 da API.
  • O -7 é apenas informativo e não afeta o processo de atualização OTA.
Portanto, um dispositivo com um HAL na versão 2.10 no arquivo de manifesto continua compatível com um framework que declara 2.5-7 na matriz de compatibilidade.

Exemplo: correspondência bem-sucedida do HAL para o módulo DRM

A matriz de compatibilidade do framework informa as seguintes informações de versão para o HAL do DRM:

<hal>
    <name>android.hardware.drm
    <version>1.0</version>
    <version>3.1-2</version>
    <interface>
        <name>IDrmFactory</name>
        <instance>default</instance>
        <instance>specific</instance>
    </interface>
</hal>
<hal>
    <name>android.hardware.drm
    <version>2.0</version>
    <interface>
        <name>ICryptoFactory</name>
        <instance>default</instance>
        <regex-instance>[a-z]+/[0-9]+</regex-instance>
    </interface>
</hal>

Um fornecedor precisa implementar UMA das seguintes instâncias:

android.hardware.drm@1.x::IDrmFactory/default          // where x >= 0
android.hardware.drm@1.x::IDrmFactory/specific         // where x >= 0
OU
android.hardware.drm@3.y::IDrmFactory/default          // where y >= 1
android.hardware.drm@3.y::IDrmFactory/specific         // where y >= 1

E também precisa implementar todas estas instâncias:

android.hardware.drm@2.z::ICryptoFactory/default       // where z >= 0
android.hardware.drm@2.z::ICryptoFactory/${INSTANCE}
            // where z >= 0 and ${INSTANCE} matches [a-z]+/[0-9]+
            // e.g. legacy/0

HALs AIDL

Todas as versões do Android mais recentes que o Android 11 (exceto o Android 11) são compatíveis com versões de HALs AIDL no VINTF. As regras de correspondência para HALs da AIDL são semelhantes às de HALs nativas e da HIDL, exceto que não há versões principais e há exatamente uma versão por instância de HAL (1 se a versão não estiver especificada).

  • Vários elementos <hal> são avaliados com uma única relação AND.
  • Os elementos <hal> podem ter <hal optional="true"> para marcá-los como não obrigatórios. Aviso: esse optional não é mais compatível com o Android 15
  • Vários elementos <instance> e <regex-instance> no mesmo <hal> são avaliados com uma única relação AND quando o <hal> é necessário. (Consulte o <ahref="#vibrator">exemplo de vibrador abaixo.)</ahref="#vibrator">

Exemplo: correspondência bem-sucedida do HAL para um módulo

Para uma HAL na versão 5, a regra de correspondência é a seguinte:

Matriz Manifesto correspondente
5 5 a ∞. Na matriz de compatibilidade, 5 é a abreviação de 5-5.
5-7 5-∞. Indica o seguinte:
  • 5 é a versão mínima necessária, o que significa que um manifesto que fornece HAL 1-4 não é compatível.
  • 7 é a versão máxima que pode ser solicitada, ou seja, o proprietário da matriz de compatibilidade (framework ou dispositivo) não vai solicitar versões além da 7. O proprietário do manifesto correspondente ainda pode veicular a versão 10 (por exemplo) quando a 7 for solicitada. O proprietário da matriz de compatibilidade sabe apenas que o serviço solicitado é compatível com a versão 7 da API.
  • O -7 é apenas informativo e não afeta o processo de atualização OTA.
Portanto, um dispositivo com um HAL na versão 10 no arquivo de manifesto continua compatível com um framework que declara 5-7 na matriz de compatibilidade.

Exemplo: correspondência bem-sucedida da HAL para vários módulos

A matriz de compatibilidade do framework informa as seguintes informações de versão para HALs de vibrador e câmera:

<hal>
    <name>android.hardware.vibrator
    <version>1-2</version>
    <interface>
        <name>IVibrator</name>
        <instance>default</instance>
        <instance>specific</instance>
    </interface>
</hal>
<hal>
    <name>android.hardware.camera
    <version>5</version>
    <interface>
        <name>ICamera</name>
        <instance>default</instance>
        <regex-instance>[a-z]+/[0-9]+</regex-instance>
    </interface>
</hal>

Um fornecedor precisa implementar todas essas instâncias:

android.hardware.vibrator.IVibrator/default     // version >= 1
android.hardware.vibrator.IVibrator/specific    // version >= 1
android.hardware.camera.ICamera/default         // version >= 5
android.hardware.camera.ICamera/${INSTANCE}
            // with version >= 5, where ${INSTANCE} matches [a-z]+/[0-9]+
            // e.g. legacy/0

Kernels correspondentes

A seção <kernel> da matriz de compatibilidade do framework descreve os requisitos do framework do kernel do Linux no dispositivo. Essas informações devem ser comparadas com as informações sobre o kernel que são relatadas pelo objeto VINTF do dispositivo.

Corresponder a ramos do kernel

Cada sufixo de ramificação do kernel (por exemplo, 5.4-r) é mapeado para uma versão única do FCM do kernel (por exemplo, 5). O mapeamento é o mesmo entre as letras de versão (por exemplo, R) e as versões do FCM (por exemplo, 5).

Os testes do VTS garantem que o dispositivo especifique explicitamente a versão do FCM do kernel no manifesto do dispositivo, /vendor/etc/vintf/manifest.xml, se um dos seguintes itens for verdadeiro:

  • A versão do FCM do kernel é diferente da versão do FCM de destino. Por exemplo, o dispositivo mencionado tem uma versão do FCM de destino 4, e a versão do FCM do kernel é 5 (sufixo de ramificação do kernel r).
  • A versão do FCM do kernel é maior ou igual a 5 (sufixo da ramificação do kernel r).

Os testes do VTS garantem que, se a versão do FCM do kernel for especificada, ela será maior ou igual à versão do FCM de destino no manifesto do dispositivo.

Exemplo: determinar a ramificação do kernel

Se o dispositivo tiver a versão 4 do FCM de destino (lançada no Android 10), mas executar o kernel do ramo 4.19-r, o manifesto do dispositivo precisará especificar o seguinte:

<manifest version="2.0" type="device" target-level="4">
   <kernel target-level="5" />
</manifest>

O objeto VINTF verifica a compatibilidade do kernel com os requisitos na ramificação do kernel 4.19-r, especificada na versão 5 do FCM. Esses requisitos são criados com base em kernel/configs/r/android-4.19 na árvore de origem do Android.

Exemplo: determinar a ramificação do kernel para GKI

Se o dispositivo usa a imagem genérica do kernel (GKI) e a string de versão do kernel de /proc/version é a seguinte:

5.4.42-android12-0-00544-ged21d463f856

Em seguida, o objeto VINTF recebe a versão do Android da versão do kernel e a usa para determinar a versão do FCM do kernel. Neste exemplo, android12 significa a versão 6 do FCM do kernel (lançada no Android 12).

Para saber como a string de versão do kernel é analisada, consulte Controle de versões do GKI.

Corresponder às versões do kernel

Uma matriz pode incluir várias seções <kernel>, cada uma com um atributo version diferente usando o formato:

${ver}.${major_rev}.${kernel_minor_rev}

O objeto VINTF considera apenas a seção <kernel> do FCM com a versão correspondente do FCM com o mesmo ${ver} e ${major_rev} do kernel do dispositivo (ou seja, version="${ver}.${major_rev}.${matrix_minor_rev}"). As outras seções são ignoradas. Além disso, a revisão secundária do kernel precisa ser um valor da matriz de compatibilidade (${kernel_minor_rev} >= ${matrix_minor_rev};). Se nenhuma seção <kernel> atender a esses requisitos, ela não será correspondente.

Exemplo: selecionar requisitos para correspondência

Considere o seguinte caso hipotético em que os FCMs em /system/etc/vintf declaram os requisitos abaixo (as tags de cabeçalho e rodapé são omitidas):

<!-- compatibility_matrix.3.xml -->
<kernel version="4.4.107" level="3"/>
<!-- See kernel/configs/p/android-4.4/ for 4.4-p requirements -->
<kernel version="4.9.84" level="3"/>
<!-- See kernel/configs/p/android-4.9/ for 4.9-p requirements -->
<kernel version="4.14.42" level="3"/>
<!-- See kernel/configs/p/android-4.14/ for 4.14-p requirements -->

<!-- compatibility_matrix.4.xml -->
<kernel version="4.9.165" level="4"/>
<!-- See kernel/configs/q/android-4.9/ for 4.9-q requirements -->
<kernel version="4.14.105" level="4"/>
<!-- See kernel/configs/q/android-4.14/ for 4.14-q requirements -->
<kernel version="4.19.42" level="4"/>
<!-- See kernel/configs/q/android-4.19/ for 4.19-q requirements -->

<!-- compatibility_matrix.5.xml -->
<kernel version="4.14.180" level="5"/>
<!-- See kernel/configs/r/android-4.14/ for 4.14-r requirements -->
<kernel version="4.19.123" level="5"/>
<!-- See kernel/configs/r/android-4.19/ for 4.19-r requirements -->
<kernel version="5.4.41" level="5"/>
<!-- See kernel/configs/r/android-5.4/ for 5.4-r requirements -->

A versão do FCM de destino, a versão do FCM do kernel e a versão do kernel selecionam os requisitos do kernel dos FCMs:

Versão do FCM de destinoVersão do FCM do kernelVersão do kernelCorresponder a
3 (P)não especificado4.4.106 Nenhuma correspondência (incompatibilidade de versão secundária)
3 (P)não especificado4.4.107 4.4-p
3 (P)não especificado4.19.42 4.19-q (consulte a observação abaixo)
3 (P)não especificado5.4.41 5.4-r (confira a observação abaixo)
3 (P)3 (P) 4.4.107 4.4-p
3 (P)3 (P) 4.19.42 Nenhuma correspondência (nenhuma ramificação do kernel 4.19-p)
3 (P)4 (Q) 4.19.42 4.19-q
4 (Q)não especificado4.4.107 Nenhuma correspondência (nenhuma ramificação do kernel 4.4-q)
4 (Q)não especificado4.9.165 4.9-q
4 (Q)não especificado5.4.41 5.4-r (confira a observação abaixo)
4 (Q)4 (Q) 4.9.165 4.9-q
4 (Q)4 (Q) 5.4.41 Nenhuma correspondência (nenhuma ramificação do kernel 5.4-q)
4 (Q)5 (R) 4.14.1054.14-r
4 (Q)5 (R) 5.4.41 5.4-r
5 (R)não especificadoqualquer O VTS falha (é necessário especificar a versão do FCM do kernel para a versão de destino 5 do FCM)
5 (R)4 (Q) qualquer VTS falha (versão do FCM do kernel < versão do FCM de destino)
5 (R)5 (R) 4.14.1804.14-r

Corresponder às configurações do kernel

Se a seção <kernel> corresponder, o processo vai continuar tentando fazer a correspondência de elementos config com /proc/config.gz. Para cada elemento de configuração na matriz de compatibilidade, ele procura /proc/config.gz para saber se a configuração está presente. Quando um item de configuração é definido como n na matriz de compatibilidade para a seção <kernel> correspondente, ele precisa estar ausente de /proc/config.gz. Por fim, um item de configuração que não está na matriz de compatibilidade pode ou não estar presente em /proc/config.gz.

Exemplo: corresponder a configurações do kernel

  • <value type="string">bar</value> corresponde "bar". As aspas são omitidas na matriz de compatibilidade, mas estão presentes em /proc/config.gz.
  • <value type="int">4096</value> corresponde a 4096 ou 0x1000 ou 0X1000.
  • <value type="int">0x1000</value> corresponde a 4096 ou 0x1000 ou 0X1000.
  • <value type="int">0X1000</value> corresponde a 4096 ou 0x1000 ou 0X1000.
  • <value type="tristate">y</value> corresponde y.
  • <value type="tristate">m</value> corresponde m.
  • <value type="tristate">n</value> significa que o item de configuração NÃO pode existir em /proc/config.gz.
  • <value type="range">1-0x3</value> corresponde a 1, 2 ou 3, ou equivalente hexadecimal.

Exemplo: correspondência bem-sucedida do kernel

Uma matriz de compatibilidade do framework com a versão 1 do FCM tem as seguintes informações do kernel:

<kernel version="4.14.42">
   <config>
      <key>CONFIG_TRI</key>
      <value type="tristate">y</value>
   </config>
   <config>
      <key>CONFIG_NOEXIST</key>
      <value type="tristate">n</value>
   </config>
   <config>
      <key>CONFIG_DEC</key>
      <value type="int">4096</value>
   </config>
   <config>
      <key>CONFIG_HEX</key>
      <value type="int">0XDEAD</value>
   </config>
   <config>
      <key>CONFIG_STR</key>
      <value type="string">str</value>
   </config>
   <config>
      <key>CONFIG_EMPTY</key>
      <value type="string"></value>
   </config>
</kernel>

A ramificação do kernel é correspondida primeiro. O branch do kernel é especificado no manifesto do dispositivo em manifest.kernel.target-level, que tem manifest.level como padrão se o primeiro não for especificado. Se a ramificação do kernel no manifesto do dispositivo:

  • é 1, prossegue para a próxima etapa e verifica a versão do kernel.
  • é 2, sem correspondência com a matriz. Os objetos VINTF leem os requisitos do kernel da matriz na versão 2 do FCM.

Em seguida, a versão do kernel é correspondida. Se um dispositivo em uname() informar:

  • 4.9.84 (não há correspondência com a matriz, a menos que haja uma seção de kernel separada com <kernel version="4.9.x">, onde x <= 84)
  • 4.14.41 (sem correspondência com a matriz, menor que version)
  • 4.14.42 (corresponde à matriz)
  • 4.14.43 (correspondência à matriz)
  • 4.1.22 (não há correspondência com a matriz, a menos que haja uma seção de kernel separada com <kernel version="4.1.x"> em que x <= 22)

Depois que a seção <kernel> adequada é selecionada, para cada item <config> com valor diferente de n, esperamos que a entrada correspondente esteja presente em /proc/config.gz. Para cada item <config> com valor n, esperamos que a entrada correspondente não esteja presente em /proc/config.gz. Esperamos que o conteúdo de <value> corresponda exatamente ao texto após o sinal de igual (incluindo aspas), até o caractere de nova linha ou #, com espaços em branco iniciais e finais truncados.

A configuração do kernel a seguir é um exemplo de correspondência bem-sucedida:

# comments don't matter
CONFIG_TRI=y
# CONFIG_NOEXIST shouldn't exist
CONFIG_DEC = 4096 # trailing comments and whitespaces are fine
CONFIG_HEX=57005  # 0XDEAD == 57005
CONFIG_STR="str"
CONFIG_EMPTY=""   # empty string must have quotes
CONFIG_EXTRA="extra config items are fine too"

A configuração do kernel a seguir é um exemplo de correspondência sem sucesso:

CONFIG_TRI="y"   # mismatch: quotes
CONFIG_NOEXIST=y # mismatch: CONFIG_NOEXIST exists
CONFIG_HEX=0x0   # mismatch; value doesn't match
CONFIG_DEC=""    # mismatch; type mismatch (expect int)
CONFIG_EMPTY=1   # mismatch; expects ""
# mismatch: CONFIG_STR is missing

Correspondências de políticas do SE

A política de SE exige as seguintes correspondências:

  • <sepolicy-version> define um intervalo fechado de versões secundárias para cada versão principal. A versão do sepolicy informada pelo dispositivo precisa estar dentro de um desses intervalos para ser compatível com o framework. As regras de correspondência são semelhantes às versões do HAL. Elas são correspondentes se a versão da sepolicy for maior ou igual à versão mínima do intervalo. A versão máxima é apenas informativa.
  • <kernel-sepolicy-version>, ou seja, a versão da policydb. Precisa ser menor que o security_policyvers() informado pelo dispositivo.

Exemplo: correspondência bem-sucedida da política de SE

A matriz de compatibilidade do framework apresenta as seguintes informações de política de segurança:

<sepolicy>
    <kernel-sepolicy-version>30</kernel-sepolicy-version>
    <sepolicy-version>25.0</sepolicy-version>
    <sepolicy-version>26.0-3</sepolicy-version>
</sepolicy>

No dispositivo:

  • O valor retornado por security_policyvers() precisa ser maior ou igual a 30. Caso contrário, não é uma correspondência. Por exemplo:
    • Se um dispositivo retornar 29, ele não será correspondente.
    • Se um dispositivo retornar 31, ele será correspondente.
  • A versão da política de SE precisa ser 25.0-∞ ou 26.0-∞. Caso contrário, não haverá correspondência. O "-3" depois de "26.0" é apenas para informação.

Correspondências de versão do AVB

A versão AVB contém uma versão PRINCIPAL e uma MINOR, com o formato como PRINCIPAL.MINOR (por exemplo, 1.0, 2.1). Para mais detalhes, consulte Controle de versões e compatibilidade. A versão AVB tem as seguintes propriedades do sistema:

  • ro.boot.vbmeta.avb_version é a versão libavb no carregador de inicialização
  • ro.boot.avb_version é a versão libavb no SO Android (init/fs_mgr).

A propriedade do sistema aparece apenas quando a libavb correspondente foi usada para verificar os metadados do AVB (e retorna "OK"). Ele está ausente se ocorreu uma falha de verificação ou se nenhuma verificação ocorreu.

Uma correspondência de compatibilidade compara o seguinte:

  • sysprop ro.boot.vbmeta.avb_version com avb.vbmeta-version da matriz de compatibilidade do framework;
    • ro.boot.vbmeta.avb_version.MAJOR == avb.vbmeta-version.MAJOR
    • ro.boot.vbmeta.avb_version.MINOR >= avb.vbmeta-version.MINOR
  • sysprop ro.boot.avb_version com avb.vbmeta-version da matriz de compatibilidade do framework.
    • ro.boot.avb_version.MAJOR == avb.vbmeta-version.MAJOR
    • ro.boot.avb_version.MINOR >= avb.vbmeta-version.MINOR

O carregador de inicialização ou o SO Android pode conter duas cópias de bibliotecas libavb, cada uma com uma versão MAJOR diferente para dispositivos de upgrade e de lançamento. Nesse caso, a mesma imagem de sistema não assinada pode ser compartilhada, mas as imagens de sistema assinhadas finais são diferentes (com avb.vbmeta-version diferentes):

Figura 1. A versão do AVB corresponde (/system é P, todas as outras partições são O).



Figura 2. A versão do AVB corresponde (todas as partições são P).

Exemplo: correspondência bem-sucedida da versão do AVB

A matriz de compatibilidade do framework apresenta as seguintes informações do AVB:

<avb>
    <vbmeta-version>2.1</vbmeta-version>
</avb>

No dispositivo:

ro.boot.avb_version              == 1.0 &&
ro.boot.vbmeta.avb_version       == 2.1  mismatch 
ro.boot.avb_version              == 2.1 &&
ro.boot.vbmeta.avb_version       == 3.0  mismatch 
ro.boot.avb_version              == 2.1 &&
ro.boot.vbmeta.avb_version       == 2.3  match 
ro.boot.avb_version              == 2.3 &&
ro.boot.vbmeta.avb_version       == 2.1  match 

Corresponder à versão do AVB durante a atualização OTA

Para dispositivos lançados com o Android 9 ou versões anteriores, ao atualizar para o Android 10, os requisitos de versão do AVB na matriz de compatibilidade do framework são comparados com a versão atual do AVB no dispositivo. Se a versão do AVB tiver um upgrade de versão principal durante uma OTA (por exemplo, de 0.0 para 1.0), a verificação de compatibilidade do VINTF na OTA não vai refletir a compatibilidade após a OTA.

Para atenuar o problema, um OEM pode colocar uma versão falsa do AVB no pacote OTA (compatibility.zip) para passar na verificação. Para fazer isso, siga estas etapas:

  1. Escolha os seguintes CLs para a árvore de origem do Android 9:
  2. Defina BOARD_OTA_FRAMEWORK_VBMETA_VERSION_OVERRIDE para o dispositivo. O valor precisa ser igual à versão do AVB antes do OTA, ou seja, a versão do AVB do dispositivo quando ele foi lançado.
  3. Recrie o pacote OTA.

Essas mudanças colocam automaticamente BOARD_OTA_FRAMEWORK_VBMETA_VERSION_OVERRIDE como compatibility-matrix.avb.vbmeta-version nos seguintes arquivos:

  • /system/compatibility_matrix.xml (que não é usado no Android 9) no dispositivo
  • system_matrix.xml em compatibility.zip no pacote OTA

Essas mudanças não afetam outras matrizes de compatibilidade do framework, incluindo /system/etc/vintf/compatibility_matrix.xml. Depois do OTA, o novo valor em /system/etc/vintf/compatibility_matrix.xml é usado para verificações de compatibilidade.

Correspondências de versão do VNDK

A matriz de compatibilidade do dispositivo declara a versão do VNDK necessária em compatibility-matrix.vendor-ndk.version. Se a matriz de compatibilidade do dispositivo não tiver uma tag <vendor-ndk>, nenhum requisito será imposto e, portanto, ele sempre será considerado uma correspondência.

Se a matriz de compatibilidade do dispositivo tiver uma tag <vendor-ndk>, uma entrada <vendor-ndk> com um <version> correspondente será pesquisada no conjunto de snapshots do fornecedor do VNDK fornecido pelo framework no manifesto do framework. Se essa entrada não existir, não haverá correspondência.

Se essa entrada existir, o conjunto de bibliotecas enumeradas na matriz de compatibilidade do dispositivo precisa ser um subconjunto do conjunto de bibliotecas declarado no manifesto do framework. Caso contrário, a entrada não será considerada uma correspondência.

  • Como caso especial, se nenhuma biblioteca for enumerada na matriz de compatibilidade do dispositivo, a entrada será sempre considerada uma correspondência, porque o conjunto vazio é um subconjunto de qualquer conjunto.

Exemplo: correspondência bem-sucedida da versão do VNDK

Se a matriz de compatibilidade do dispositivo indicar o seguinte requisito no VNDK:

<!-- Example Device Compatibility Matrix -->
<vendor-ndk>
    <version>27</version>
    <library>libjpeg.so</library>
    <library>libbase.so</library>
</vendor-ndk>

No manifesto do framework, apenas a entrada com a versão 27 é considerada.

<!-- Framework Manifest Example A -->
<vendor-ndk>
    <version>27</version>
    <library>libjpeg.so</library>
    <library>libbase.so</library>
    <library>libfoo.so</library>
</vendor-ndk>

O exemplo A é uma correspondência, porque a versão 27 do VNDK está no manifesto do framework e em {libjpeg.so, libbase.so, libfoo.so} ⊇ {libjpeg.so, libbase.so}.

<!-- Framework Manifest Example B -->
<vendor-ndk>
    <version>26</version>
    <library>libjpeg.so</library>
    <library>libbase.so</library>
</vendor-ndk>
<vendor-ndk>
    <version>27</version>
    <library>libbase.so</library>
</vendor-ndk>

O exemplo B não é uma correspondência. Embora a versão 27 do VNDK esteja no manifesto do framework, o libjpeg.so não tem suporte do framework nesse instantâneo. A versão 26 do VNDK é ignorada.

Versão do SDK do sistema correspondente

A matriz de compatibilidade do dispositivo declara um conjunto de versões do SDK do sistema necessárias em compatibility-matrix.system-sdk.version. Há uma correspondência somente se o conjunto for um subconjunto das versões do SDK do sistema fornecidas, conforme declarado em manifest.system-sdk.version no manifesto do framework.

  • Como caso especial, se nenhuma versão do SDK do sistema for enumerada na matriz de compatibilidade do dispositivo, ela sempre será considerada uma correspondência, porque o conjunto vazio é um subconjunto de qualquer conjunto.

Exemplo: correspondência bem-sucedida da versão do SDK do sistema

Se a matriz de compatibilidade do dispositivo indicar o seguinte requisito no SDK do sistema:

<!-- Example Device Compatibility Matrix -->
<system-sdk>
    <version>26</version>
    <version>27</version>
</system-sdk>

Em seguida, o framework precisa fornecer as versões 26 e 27 do SDK do sistema para fazer a correspondência.

<!-- Framework Manifest Example A -->
<system-sdk>
    <version>26</version>
    <version>27</version>
</system-sdk>

O exemplo A é uma correspondência.

<!-- Framework Manifest Example B -->
<system-sdk>
    <version>26</version>
    <version>27</version>
    <version>28</version>
</system-sdk>

O exemplo B é uma correspondência.

<!-- Framework Manifest Example C -->
<system-sdk>
    <version>26</version>
</system-sdk>

O exemplo C não corresponde, porque a versão 27 do SDK do sistema não é fornecida.