Processus de création du service HIDL - basé sur l'analyse Android 12 S

Table des matières

Comment ajouter le service HIDL

1. Ajouter le dossier du service HiDL

2. Ajoutez un fichier .hal

3. Compilez hidl-gen

4. Configurez la racine du package de hidl

5. Générez des fichiers .cpp et .h sous 1.0/default/

6. Générez Android.bp sous 1.0/default/

7. Générez Android.bp sous 1.0

8. Exécutez la commande suivante dans le répertoire principal Android pour générer current.txt

9. Ajoutez supplier.qti.hardware.customizehidl-service.rc sous 1.0/default/

10. Ajoutez supplier.qti.hardware.customizehidl-service.xml sous 1.0/default/

11. Ajoutez le contenu suivant dans device/qcom/common/vendor_compatibility_matrix.xml

12. Ajoutez service.cpp sous 1.0/default/

13. Écrivez un programme de test bin

14. Testez

14.1 Méthode de compilation unique :

14.2 Méthode d'essai :

15. Problèmes possibles

15.1 Erreur 1

15.2 Ajouter un nouveau répertoire pour mettre le service hal

16. Ajouter un service Hal personnalisé Selinux


Le but du mécanisme HIDL est principalement d'isoler le framework (framework) du HAL, afin que la partie framework puisse être directement écrasée et mise à jour sans recompiler le HAL. Des parties du HAL seront placées dans la partition /vendor de l'appareil et construites par les fournisseurs d'appareils (fournisseurs) ou les fabricants de SOC. Cela permet aux parties du framework d'être mises à jour OTA sans recompiler le HAL.

Cette conception s'appelle le mécanisme Treble, introduit à partir d'Android 8.0. Avant cela, le framework doit appeler dlopen pour ouvrir le .so compilé par HAL afin de communiquer avec la couche HAL. De cette façon, le framework et HAL sont dans le même processus, et le couplage entre les deux est sérieux, ce qui oblige le fournisseur à faire un gros travail d'adaptation lors de la mise à niveau de la version.

       Le mécanisme Treble résout le problème des mises à niveau gênantes entre les versions actuelles d'Android. Il sépare la partie du fournisseur adaptée par l'OEM de la partie du système du framework Android mise à niveau par Google. Une fois les informations du fournisseur d'une version adaptées, la version suivante sera mise à jour Lors de la mise à niveau, vous pouvez directement mettre à niveau le système, ce qui n'apportera pas trop de charge de travail au fabricant OEM pour la mise à niveau, et mettre à niveau directement les dernières fonctions, ce qui peut résoudre le problème de la version actuelle d'Android sur le marché est trop compliqué.

Le mécanisme Treble a deux modes dans la partition Vendor, le mode passthrough (Passthrough) et le mode liaison (Binderized). Le schéma général du cadre est le suivant. Pour les appareils antérieurs à Android O, il correspond à la figure 1. Pour la version mise à niveau par rapport à la précédente appareil à O , correspondant à la figure 2 et à la figure 3. Pour les appareils développés directement basés sur Android O, cela correspond à la figure 4.

Généralement, les nouveaux services HIDL sont ajoutés sous le répertoire du fournisseur. Il est préférable d'ajouter des dossiers sous votre propre nom de produit et de créer les services HIDL correspondants. En supposant que vous souhaitiez ajouter des services HIDL sous qcom, le processus est le suivant :

Comment ajouter le service HIDL

1. Ajouter le dossier du service HiDL

Ajoutez un nouveau dossier sous supplier/qcom/opensource/interfaces, ajoutez un dossier personnaliserhidl ici

Créez un nouveau dossier 1.0 sous personnaliserhidl

Ajouter un dossier par défaut sous 1.0

2. Ajoutez un fichier .hal

Ajoutez les fichiers ICustomizehidl.hal et types.hal sous personnaliserhidl

vendor/qcom/opensource/interfaces/ICustomizehidl.hal
package [email protected];

interface ICustomizeHidl{
    resetOption(int32_t side) generates (Result result);
};
vendor/qcom/opensource/interfaces/types.hal
package [email protected];

enum Result : int32_t {
    OK = 0,
    ERR,
    OUT_OF_RANGE,
};

3. Compilez hidl-gen

    source build/envsetup.sh

    déjeuner xx

    créer un générateur de filtre

De cette façon, l'outil hidl-gen peut être utilisé plus tard ,

4. Configurez la racine du package de hidl

    PACKAGE=vendor.qti.hardware. personnaliserhidl @1.0

    LOC=vendor/qcom/opensource/interfaces/ customizehidl /1.0/default/

S'il y a une erreur comme suit

ERREUR : racine du package non spécifiée pour [email protected]

ERREUR : impossible d'obtenir les sources de [email protected].

Vous devez ajouter le code suivant dans le répertoire suivant :

vendor/qcom/opensource/interfaces/Android.bp

hidl_package_root {
    name:"vendor.qti.hardware.customizehidl",
    path:"vendor/qcom/opensource/interfaces/customizehidl",
}  

5. Générez des fichiers .cpp et .h sous 1.0/default/

Générez des fichiers .cpp et .h sous supplier/qcom/opensource/interfaces/ customizehidl /1.0/default/ :

hidl-gen -o $LOC -Lc++-impl -rvendor.qti.hardware:vendor/qcom/opensource/interfaces -randroid.hidl:system/libhidl/transport $PACKAGE

ou

hidl-gen -o seller/qcom/opensource/interfaces/ customizehidl /1.0/default -Lc++-impl -rvendor.qti.hardware:vendor/qcom/opensource/interfaces –randroid.hidl:system/libhidl/transport seller.qti. matériel. personnaliserhidl @1.0

Ensuite, les fichiers CustomizeHidl.cpp et CustomizeHidl.h sont générés. Les modifications pertinentes doivent être apportées après la génération. Le contenu modifié est le suivant :

vendor/qcom/opensource/interfaces/customizehidl/1.0/default/CustomizeHidl.cpp
#include "CustomizeHidl.h"
#include <pthread.h>
#include <sched.h>
#include <map>

#include <fcntl.h>
#include <unistd.h>

namespace vendor {
namespace qti {
namespace hardware {
namespace customizehidl {
namespace V1_0 {
namespace implementation {

CustomizeHidl::CustomizeHidl() {
}

CustomizeHidl::~CustomizeHidl() {
}

Return<::vendor::qti::hardware::customizehidl::V1_0::Result> CustomizeHidl::resetOption(int32_t side) {
    return ::vendor::qti::hardware::customizehidl::V1_0::Result {};
}

// Methods from ::android::hidl::base::V1_0::IBase follow.
//ICustomizeHidl* HIDL_FETCH_ICustomizeHidl(const char* /* name */) {
//    return new CustomizeHidl();
//}
//
}  // implementation
}  // V1_0
}  // customizehidl
}  // hardware
}  // qti
}  // vendor

 Le contenu du fichier d'en-tête est le suivant :

vendor/qcom/opensource/interfaces/customizehidl/1.0/default/CustomizeHidl.h
#include <vendor/qti/hardware/customizehidl/1.0/ICustomizeHidl.h>
#include <hidl/MQDescriptor.h>
#include <hidl/Status.h>
#include <fstream>
#include <iostream>

namespace vendor {
namespace qti {
namespace hardware {
namespace customizehidl {
namespace V1_0 {
namespace implementation {

using namespace std;
using ::android::hardware::hidl_array;
using ::android::hardware::hidl_memory;
using ::android::hardware::hidl_string;
using ::android::hardware::hidl_vec;
using ::android::hardware::Return;
using ::android::hardware::Void;
using ::android::sp;

struct CustomizeHidl : public ICustomizeHidl {
    CustomizeHidl();
    ~CustomizeHidl();
    Return<::vendor::qti::hardware::customizehidl::V1_0::Result> resetOption(int32_t side) override;

};

// FIXME: most likely delete, this is only for passthrough implementations
// extern "C" ICustomizeHidl* HIDL_FETCH_ICustomizeHidl(const char* name);

}  // implementation
}  //customizehidl
}  // V1_0
}  // hardware
}  // qti
}  // vendor

6. Générez Android.bp sous 1.0/default/

Générez Android.bp sous supplier/qcom/opensource/interfaces/ customizehidl /1.0/default/ :

hidl-gen -o $LOC -Landroidbp-impl -rvendor.qti.hardware:vendor/qcom/opensource/interfaces -randroid.hidl:system/libhidl/transport $PACKAGE

Les modifications pertinentes doivent être apportées après la génération. Le contenu modifié est le suivant :

cc_defaults{
    name: "customizehidl_defaults",
    //relative_install_path: "hw",
    defaults: ["hidl_defaults"],
    //根据项目需求
    //vendor: true,
    proprietary: true,
    cflags: [
       "-Wno-unused-parameter",
       "-Wall",
    ],
    shared_libs: [
            "libcutils",
            "liblog",
            "libbase",
            "libsysutils",
            "libhidlbase",
            "libhidltransport",
            "libutils",
            "[email protected]",
        ],

}

cc_library_shared {
    name: "[email protected]",
    relative_install_path: "hw",
    //根据项目需求
    //vendor: true,
    proprietary: true,
    cflags: [
           "-Wno-unused-parameter",
           "-Wall",
           "-Wunused-variable",
           "-Wunused-const-variable",
           "-Wunused-variable",
    ],
    srcs: [
        "CustomizeHidl.cpp",
    ],
    defaults: ["customizehidl_defaults"],
}

cc_binary {
    name: "[email protected]",
    proprietary: true,
    compile_multilib: "both",
    relative_install_path: "hw",
    defaults: ["customizehidl_defaults"],
    //rc引用
    init_rc: ["vendor.qti.hardware.customizehidl-service.rc"],
    //vintf_fragments引用
    vintf_fragments: ["vendor.qti.hardware.customizehidl-service.xml"],
    srcs: [
        "service.cpp",
    ],
    shared_libs: [
        "libcutils",
        "liblog",
        "libbase",
        "libsysutils",
        "libhidlbase",
        "libhidltransport",
        "libutils",
        "[email protected]",
    ],

}

7. Générez Android.bp sous 1.0

Générez Android.bp sous supplier/qcom/opensource/interfaces/ customizehidl /1.0

source système/tools/hidl/update-makefiles-helper.sh

do_makefiles_update supplier.qti.hardware:vendor/qcom/opensource/interfaces android.hardware:hardware/interfaces android.hidl:system/libhidl/transport

Les modifications pertinentes doivent être apportées après la génération. Le contenu modifié est le suivant :

hidl_interface {
    name: "[email protected]",
    root: "vendor.qti.hardware.customizehidl",
    //根据需求进行设置
    //product_specific: true,
    system_ext_specific: true,
    srcs: [
        "types.hal",
        "ICustomizeHidl.hal",
    ],
    interfaces: [
        "[email protected]",
    ],
    gen_java: true,
}

8. Exécutez la commande suivante dans le répertoire principal Android pour générer current.txt

hidl-gen -Lhash -rvendor.qti.hardware:vendor/qcom/opensource/interfaces -randroid.hidl:system/libhidl/transport seller.qti.hardware. personnaliserhidl @1.0 > vendeur/qcom/opensource/interfaces/ customiserhidl /current.txt

9. Ajoutez supplier.qti.hardware.customizehidl -service.rc sous 1.0/default/

Ajoutez le contenu suivant

service vendor.qti.hardware.customizehidl-1-0 /vendor/bin/hw/[email protected]
class hal
user system
group system

10. Ajoutez supplier.qti.hardware.customizehidl-service.xml sous 1.0/default/

<manifest version="1.0" type="device">
    <hal format="hidl">
        <name>vendor.qti.hardware.customizehidl</name>
        <transport>hwbinder</transport>
        <version>1.0</version>
        <interface>
            <name>ICustomizeHidl</name>
            <instance>default</instance>
        </interface>
    </hal>
</manifest>

11. Ajoutez le contenu suivant dans device/qcom/common/vendor_compatibility_matrix.xml (je ne l'ai pas ajouté ici, il peut toujours fonctionner)

    <hal format="hidl" optional="true">
        <name>vendor.qti.hardware.customizehidl</name>
        <transport>hwbinder</transport>
        <version>1.0</version>
        <interface>
            <name>ICustomizeHidl</name>
            <instance>default</instance>
        </interface>
    </hal>

12. Ajoutez service.cpp sous 1.0/default/

Si la méthode Binderisée est utilisée, comme suit

#include <android-base/logging.h>
#include <hidl/HidlTransportSupport.h>
#include "CustomizeHidl.h"
#include <utils/Log.h>
#include <hidl/LegacySupport.h>
using namespace android;
using vendor::qti::hardware::customizehidl::V1_0::ICustomizeHidl;
using vendor::qti::hardware::customizehidl::V1_0::implementation::CustomizeHidl;
using android::hardware::configureRpcThreadpool;
using android::hardware::joinRpcThreadpool;
using android::sp;

int main(int /* argc */, char ** /* argv */) {
    sp<ICustomizeHidl> service = new CustomizeHidl();
    configureRpcThreadpool(1, true /*callerWillJoin*/);
    if (::android::OK != service->registerAsService()) {
        return -1;
    }
    joinRpcThreadpool();
    return 0;
}

Si vous souhaitez utiliser la méthode Passthrough, vous devez écrire main comme suit, mais en même temps, vous devez publier la méthode HIDL_FETCH_ICustomizeHidl dans CustomizeHidl.cpp et CustomizeHidl.h.

#include <android-base/logging.h>
#include <hidl/HidlTransportSupport.h>
#include "CustomizeHidl.h"
#include <utils/Log.h>
#include <hidl/LegacySupport.h>
using namespace android;
using vendor::qti::hardware::customizehidl::V1_0::ICustomizeHidl;
using android::hardware::configureRpcThreadpool;
using android::hardware::joinRpcThreadpool;
using android::hardware::defaultPassthroughServiceImplementation;
using android::hardware::registerPassthroughServiceImplementation;

int main() {
	android::status_t status;

	configureRpcThreadpool(10, false);
	status = registerPassthroughServiceImplementation<ICustomizeHidl>();

	LOG_ALWAYS_FATAL_IF(status != OK, "Error while registering ICustomizeHidl: %d", status);

	joinRpcThreadpool();
	return status;
}

13. Écrivez un programme de test bin

Ajoutez un répertoire hidl_test_bin sous supplier/qcom/opensource/interfaces/ customizehidl / et ajoutez Android.bp

cc_binary {
    name: "hidl_test_bin",
                                                                                                                                                                                         
    srcs: [
        "hidl_test_bin.cpp",
    ],  
    shared_libs: [
        "libcutils",
        "libutils",
        "liblog",
//以下so一定要添加,否则可能会有报错
        "libbinder",
        "libhidlbase",
        "libbase",
        "libhidltransport",
        "[email protected]",
    ],  

    cflags: [
        "-Werror",
        "-Wno-error=deprecated-declarations",
        "-Wno-unused-parameter",
        "-Wall",
    ],  
}

Ajouter le fichier hidl_test_bin.cpp

#define LOG_TAG "hidl_test_bin"
#include <binder/IPCThreadState.h>
#include <binder/IServiceManager.h>
#include <binder/ProcessState.h>
#include <cutils/properties.h>
#include <fcntl.h>
#include <utils/Log.h>
#include <iostream>
#include <vendor/qti/hardware/customizehidl/1.0/ICustomizeHidl.h>
#include <vendor/qti/hardware/customizehidl/1.0/types.h>

using namespace android;
using namespace std;
using vendor::qti::hardware::customizehidl::V1_0::ICustomizeHidl;
using vendor::qti::hardware::customizehidl::V1_0::Result;
using android::hardware::Return;
using android::hardware::details::return_status;
using android::hardware::Void;
sp<ICustomizeHidl> halService;

int main(int argc, char* argv[]) {
    halService = ICustomizeHidl::getService();
    if (halService == NULL){
        cout << "get hal service failed" <<endl;
        return -1; 
    }   
    cout << "get hal service scuess" <<endl;
    float value = stof(argv[1]);
    cout << "value is " << value <<endl;
    halService->resetOption(value);
    return 0;
}

14. Testez

14.1 Méthode de compilation unique :

    source build/envsetup.sh

    déjeuner xxx

    vendeur de cd/qcom/opensource/interfaces/ customizehidl

    mma (compilation liée au service HiDL)

    vendeur de cd/qcom/opensource/interfaces/ customizehidl/ hidl_test_bin

    mma (lié au bac de test compilé)

14.2 Méthode d'essai :

1. adb pull supplier/etc/vintf/compatibility_matrix.xml

在最后增加
    <hal format="hidl" optionnel="true">
        <name>vendor.qti.hardware.customizehidl</name>
        <transport>hwbinder</transport>
        <version>1.0</version>
        <interface>
            < name>ICustomizeHidl</name>
            <instance>default</instance>
        </interface>
    </hal>

2. Repoussez à nouveau

adb racine
adb remontage

adb push compatibilité_matrix.xml fournisseur/etc/vintf/compatibility_matrix.xml

3. Exécuter sous out/target/product/qssi

adb push ./product/lib/[email protected] product/lib/
adb push ./product/lib64/[email protected] product/lib64/
adb push ./ vendeur/lib/hw/[email protected] vendeur/lib/hw/
adb push ./vendor/lib/[email protected] vendeur/lib/
adb push ./vendor/lib64/hw/[email protected] seller/lib64/hw/
adb push ./vendor/lib64/[email protected] seller/lib64/
adb push ./vendor/etc/vintf/manifest/vendor.qti.hardware.customizehidl-service.xml supplier/etc/vintf/manifest
adb push ./vendor/bin/hw/[email protected] fournisseur de services/bin/hw/
adb push ./system_ext/lib/[email protected] system_ext/lib/
adb push ./system_ext/lib64/[email protected] system_ext/lib64/
adb push system/ bin/hidl_test_bin system/bin (programme bin testé)
, puis exécutez
adb reboot
pour redémarrer et
fermer selinux : adb shell setenforce 0
window 1 : démarrer le service hidl
adb shell
cd supplier/bin/hw
./vendor.qti.hardware.customizehidl@ 1.0 -service


Fenêtre 2 : Démarrez le programme test bin   
adb shell
hidl_test_bin 100


Observez ensuite le résultat de la fenêtre 2.
Si le résultat est le suivant, cela signifie que la communication entre les deux est réussie.
Obtenez
la valeur scuess du service hal est 100

15. Problèmes possibles

15.1 Erreur 1

04-14 12:27:02.103 599 599 I hwservicemanager: getTransport: Impossible de trouver l'entrée [email protected]::ICustomizeHidl/default dans le manifeste VINTF du framework ou du périphérique.
04-14 12:27:02.104 4169 4169 E HidlServiceManagement : Service [email protected]::ICustomizeHidl/default doit être dans le manifeste VINTF pour pouvoir s'inscrire/obtenir

Autrement dit, il y a un problème avec la configuration liée au manifeste vintf. Vous pouvez vérifier s'il existe un fichier manifeste push correspondant, si le contenu de l'interface est écrit correctement, etc.

15.2 Ajouter un nouveau répertoire pour mettre le service hal

Si le répertoire nouvellement créé ne peut pas compiler les fichiers associés à hidl out pertinents, vous devez ajouter le fichier update-makefiles.sh, qui peut être copié à partir d'autres répertoires hidl et modifier le répertoire.

définir -e

si [ -z "$ANDROID_BUILD_TOP" ]; puis
    faites écho "Variable d'environnement ANDROID_BUILD_TOP manquante. Exécutez d'abord 'déjeuner'."
    sortie 1
fi

source $ANDROID_BUILD_TOP/system/tools/hidl/update-makefiles-helper.sh

do_makefiles_update \
  "fournisseur/nouveau nom/interfaces/ customizehidl "

16. Ajouter un service Hal personnalisé Selinux

Veuillez vous référer à mon autre article

Ajouter des autorisations selinux de service Hal personnalisées_Allez sur le blog de (◍>∇<◍)ノ゙

Je suppose que tu aimes

Origine blog.csdn.net/weixin_41028555/article/details/130424627
conseillé
Classement