LED灯系统架构(基于google源码分析)

2021-10-27  本文已影响0人  赛非斯
hardware/interfaces/light/2.0/default/Light.cpp
light_state_t legacyState {
        .ledId = state.ledId,

hardware/interfaces/+/474/1/light/2.0/types.hal
truct LightState {
     uint32_t ledId;

hardware/libhardware/include/hardware/lights.h
struct light_state_t {
    unsigned int ledId;

这个时候去编译,会编译报错,因为要更新api,根据报错信息修改
添加接口后会报错
c++_headers/gen -L c++-headers -randroid.hardware:hardware/interfaces -randroid.hidl:system/libhidl/transport android.hardware.light@2.0
ERROR: android.hardware.light@2.0::types has hash 6449fbfe75742a10327e8abf89d7f0855ef4c726246f3926078ec8371bb667ec which does not match hash on record. This interface has been frozen. Do not change it!
ERROR: Could not parse android.hardware.light@2.0::types. Abor
将刚刚得到的新 hashcode 值更新到 hardware/interfaces/current.txt 重新编译即可

单独编译模块或者全编译 会出现一个VNDk异常的报错

 make android.hardware.light@2.0 -j24 
make android.hardware.light@2.0-impl -j24

[ 92% 36/39] //hardware/interfaces/light/2.0:android.hardware.light@2.0 header-abi-diff android.hardware.light@2.0.so.abidiff
FAILED: out/soong/.intermediates/hardware/interfaces/light/2.0/android.hardware.light@2.0/android_arm64_armv8-a_kryo300_vendor_shared/android.hardware.light@2.0.so.abidiff
(prebuilts/clang-tools/linux-x86/bin/header-abi-diff -allow-unreferenced-changes -allow-unreferenced-elf-symbol-changes -lib android.hardware.light@2.0 -arch arm64 -o 'out/soong/.intermediates/hardware/interfaces/light/2.0/android.hardware.light@2.0/android_arm64_armv8-a_kryo300_vendor_shared/android.hardware.light@2.0.so.abidiff' -new 'out/soong/.intermediates/hardware/interfaces/light/2.0/android.hardware.light@2.0/android_arm64_armv8-a_kryo300_vendor_shared/android.hardware.light@2.0.so.lsdump' -old prebuilts/abi-dumps/vndk/29/64/arm64_armv8-a/source-based/android.hardware.light@2.0.so.lsdump)|| (echo 'error: Please update ABI references with: $ANDROID_BUILD_TOP/development/vndk/tools/header-checker/utils/create_reference_dumps.py  -l android.hardware.light@2.0' && (mkdir -p $DIST_DIR/abidiffs && cp 'out/soong/.intermediates/hardware/interfaces/light/2.0/android.hardware.light@2.0/android_arm64_armv8-a_kryo300_vendor_shared/android.hardware.light@2.0.so.abidiff' $DIST_DIR/abidiffs/) && exit 1)
******************************************************
error: VNDK library: android.hardware.light@2.0's ABI has INCOMPATIBLE CHANGES Please check compatibility report at: out/soong/.intermediates/hardware/interfaces/light/2.0/android.hardware.light@2.0/android_arm64_armv8-a_kryo300_vendor_shared/android.hardware.light@2.0.so.abidiff
******************************************************
error: Please update ABI references with: $ANDROID_BUILD_TOP/development/vndk/tools/header-checker/utils/create_reference_dumps.py  -l android.hardware.light@2.0
15:57:58 ninja failed with: exit status 1

解决:

development/vndk/tools/header-checker/utils/create_reference_dumps.py -l android.hardware.light@2.0 -products kona
development/vndk/tools/header-checker/utils/create_reference_dumps.py -product kona

log:
Creating dumps for target_arch: arm and variant armv8-2a
Created abi dump at /prebuilts/abi-dumps/vndk/29/64/arm_armv8-2a/source-based/android.hardware.light@2.0.so.lsdump
Creating dumps for target_arch: arm64 and variant armv8-a
Created abi dump at /prebuilts/abi-dumps/vndk/29/64/arm64_armv8-a/source-based/android.hardware.light@2.0.so.lsdump
再make 还是报错
问题原因 .soon下面的缓存没clean
rm -rf out/soong/.intermediates/hardware/interfaces/light 重新编译后正常

单独模块验证:

make android.hardware.light@2.0-impl -j24
 make android.hardware.light@2.0 -j24
adb push system\lib64\vndk-29\android.hardware.light@2.0.so system/lib64/vndk-29/
adb push  system\lib\vndk-29\android.hardware.light@2.0.so system/lib/vndk-29/
adb push  vendor\lib\hw\android.hardware.light@2.0-impl.so vendor/lib/hw
adb push vendor\lib64\hw\android.hardware.light@2.0-impl.so vendor/lib64/hw

static struct hw_module_methods_t lights_module_methods = {
    .open =  open_lights,
};

static int open_lights(const struct hw_module_t* module, char const* name,
        struct hw_device_t** device)
{
    int (*set_light)(struct light_device_t* dev,
            struct light_state_t const* state);

    if (0 == strcmp(LIGHT_ID_BACKLIGHT, name)) {
        g_has_persistence_node = !access(PERSISTENCE_FILE, F_OK);
        set_light = set_light_backlight;
    } else if (0 == strcmp(LIGHT_ID_BATTERY, name))
        set_light = set_light_battery;
}
/**
 * The parameters that can be set for a given light.
 *
 * Not all lights must support all parameters.  If you
 * can do something backward-compatible, you should.
 */
struct light_state_t {
    unsigned int ledId;
    unsigned int batteryState;
}

本文只展示google开源代码,具体实现不便展示

frameworks\base\services\core\jni\com_android_server_lights_LightsService.cpp
static void setLight_native(
        JNIEnv* /* env */,
        jobject /* clazz */,
        jint light,
        jint ledId,
        jint batteryState,
        jint colorARGB,
        jint flashMode,
        jint onMS,
        jint offMS,
        jint brightnessMode) {
    if (!sLightSupported) {

2、frameworks\base\services\core\java\com\android\server\lights\LightsService.java

  static native void setLight_native(int light,int ledId,int batteryState, int color, int mode,
            int onMS, int offMS, int brightnessMode);

《添加新接口流程已经完结》
-【扩展】 如何添加一个系统服务管控LED,系统已经有一个服务LightsService.java,我们需要再添加一个对外提供接口
1、frameworks\base\core\java 目录创建一个全局类XXXX.java
获取一个上下文,不需要应用传参

 private static Context getContext() {
        ActivityThread thread = ActivityThread.currentActivityThread();
        if (thread != null) {
            return (Context) thread.getApplication();
        } else {
            return null;
        }
    }

2、编写静态接口方法

    public static void xxxx(int eventId) {
        Context context = getContext();
        if (context != null) {
            if(xxxManger==null) {
                xxxManger= new xxxManger(context);
            }
                xxxManger.xxxxFun(eventId);

        } else {
            Log.e(TAG, "xxx: context is null");
        }
    }

3、xxxManger.java 编写aidl调用方法

private synchronized IxxxMangerService getService() {
        if (mService == null) {
            mService = IxxxMangerService .Stub.asInterface(
                    ServiceManager.getService("xxxservice"));
            if (mService == null) {
                Log.w("xxxxManger", "warning: no CWDEIVCE_SERVICE");
            }
        }
        return mService;
    }
  public void xxxxFun(int eventId) {
        try {
            final IxxxMangerService cvc = getService();
            if (cvc != null) {
                cvc.xxxxFun(eventId);
            }
        } catch (RemoteException ex) {
            throw ex.rethrowFromSystemServer();
        }
    }

4、同目录添加aidl
frameworks\base\core\java\IxxxMangerService.aidl
interface IxxxMangerService {
void xxxxFun(int eventId);
}
5、实现aidl的具体方法
public class xxxMangerService extends IxxxMangerService.Stub{
}
6、把此服务开机启动

frameworks\base\services\java\com\android\server\SystemServer.java
 xxxMangerService = new xxxMangerService (mSystemContext);
            ServiceManager.addService("xxxservice", xxxMangerService );

7、添加权限

------------------------------ private/service.te ------------------------------
index a8ee1955..c8248025 100644
@@ -5,3 +5,5 @@ type gsi_service,                   service_manager_type;
 type incidentcompanion_service,     system_api_service, system_server_service, service_manager_type;
 type stats_service,                 service_manager_type;
 type statscompanion_service,        system_server_service, service_manager_type;
+type led_service,     system_api_service, system_server_service, service_manager_type;
+

--------------------------- private/service_contexts ---------------------------
index 96d553bf..ee12cbed 100644
@@ -219,4 +219,5 @@ wificond                                  u:object_r:wificond_service:s0
 wifiaware                                 u:object_r:wifiaware_service:s0
 wifirtt                                   u:object_r:rttmanager_service:s0
 window                                    u:object_r:window_service:s0
+xxxservice                             u:object_r:led_service:s0
动态设置电池
dumpsys battery set level 1  (电池电量)

dumpsys battery set status 2  (电池电量)      
BATTERY_STATUS_INVALID = 0;
BATTERY_STATUS_UNKNOWN = 1;
BATTERY_STATUS_CHARGING = 2;
BATTERY_STATUS_DISCHARGING = 3;
BATTERY_STATUS_NOT_CHARGING = 4;
BATTERY_STATUS_FULL = 5;

设置电池温度
dumpsys battery set temp 560
动态设置数据库
adb shell settings put global device_provisioned 1
adb shell settings put secure user_setup_complete 1

adb shell settings put global device_provisioned 0
adb shell settings put secure user_setup_complete 0

adb shell settings get global device_provisioned 
adb shell settings get secure user_setup_complete 

以battery 的命令为例
frameworks\base\services\core\java\com\android\server\BatteryService.java

定义一个内部类
        private final class BinderService extends Binder {
            @Override protected void dump(FileDescriptor fd, PrintWriter pw, String[] args) {
                if (!DumpUtils.checkDumpPermission(mContext, TAG, pw)) return;

                if (args.length > 0 && "--proto".equals(args[0])) {
                    dumpProto(fd);
                } else {
                    dumpInternal(fd, pw, args);
                }
            }

            @Override public void onShellCommand(FileDescriptor in, FileDescriptor out,
                    FileDescriptor err, String[] args, ShellCallback callback,
                    ResultReceiver resultReceiver) {
                (new Shell()).exec(this, in, out, err, args, callback, resultReceiver);
            }
        }

发布
@Override
    public void onStart() {
        registerHealthCallback();

        mBinderService = new BinderService();
        publishBinderService("battery", mBinderService);
}
上一篇下一篇

猜你喜欢

热点阅读