MTK刷机总是出错status_shundown_cmd_exception

img

使用MTK刷机工具,总是弹出这个错误,是怎么回事?
驱动重新装了几次,也在MTK官网下载了最新的刷机软件,仍然是这个错误,求解答!

不知道你这个问题是否已经解决, 如果还没有解决的话:
  • 你可以看下这个问题的回答https://ask.csdn.net/questions/770806
  • 我还给你找了一篇非常好的博客,你可以看看是否有帮助,链接:MTK客制化切换开机动画,恢复出厂设置开机动画不变更
  • 除此之外, 这篇博客: MTK 关机充电时充电IC正常,电池正常充电,但是充电动画一直显示0%中的 相关说明 部分也许能够解决你的问题, 你可以仔细阅读以下内容或者直接跳转源博客中阅读:

    只截取部分记录一下思路
    on charger 触发
    工程中的一些on charger配置用于开机时(bootmode is charger)充电触发。
    如:device\mediatek\mt8168\init.mt8168.rc

    on charger
        wait /sys/bus/platform/devices/mt6357-charger-type-detection 10
        symlink /dev/block/platform/soc/11230000.mmc /dev/block/platform/bootdevice
        # mount ext4 /dev/block/platform/bootdevice/by-name/system /system ro wait
    
        # Permissions for System Server and daemons.
        chown system system /sys/power/autosleep
        chown system system /sys/power/state
        chown system system /sys/power/wakeup_count
        chown radio wakelock /sys/power/wake_lock
        chown radio wakelock /sys/power/wake_unlock
        chmod 0660 /sys/power/state
        chmod 0660 /sys/power/wake_lock
        chmod 0660 /sys/power/wake_unlock
        chmod 0660 /sys/power/wakeup_count
        start kpoc_charger
    
        chmod 0666 /dev/kmsg
        chmod 0775 /mnt/vendor
        mkdir /mnt/vendor/nvcfg
        mount ext4 /dev/block/platform/bootdevice/by-name/nvcfg /mnt/vendor/nvcfg rw wait
        chown system system /mnt/vendor/nvcfg
        chmod 0771 /mnt/vendor/nvcfg
        restorecon_recursive /mnt/vendor/nvcfg
        write /sys/devices/platform/battery_meter/FG_daemon_log_level 7
        write /sys/bus/platform/devices/battery/FG_daemon_log_level 7
        start fuelgauged
        start fuelgauged_nvram
    
        chown system system /sys/class/leds/lcd-backlight/brightness
        chown system system /sys/class/leds/red/brightness
        chown system system /sys/class/leds/green/brightness
    
    #    start vendor.light-default
    
        # disable USB
        write /sys/devices/platform/mt_usb/cmode 0
    

    hardware\interfaces\health\2.1\default\android.hardware.health@2.1-service.rc

    service health-hal-2-1 /vendor/bin/hw/android.hardware.health@2.1-service
        class hal charger
        user system
        group system
        capabilities WAKE_ALARM BLOCK_SUSPEND
        file /dev/kmsg w
    

    vendor\mediatek\proprietary\external\charger 关机充电时调用的服务。
    kpoc_charger.rc内容:

    on charger
        start kpoc_charger
    
    service kpoc_charger /system/bin/kpoc_charger
        class charger
        group system wakelock
        capabilities BLOCK_SUSPEND SYS_ADMIN SYS_BOOT
    

    启动流程(\system\core\init\init.cpp)中判断是否充电模式开机判断如下:

    int SecondStageMain(int argc, char** argv) {
    。。。
    
        // Don't mount filesystems or start core system services in charger mode.
        std::string bootmode = GetProperty("ro.bootmode", "");
    	LOG(INFO) << "init : xmhxj debug : bootmode is " << bootmode;
        if (bootmode == "charger") {
            am.QueueEventTrigger("charger");
        } else {
            am.QueueEventTrigger("late-init");
        }
    。。。
    }
    

    hardware\interfaces\health 提供vendor和system的接口调用。
    如电量获取getCapacity:
    hardware\interfaces\health\2.0\default\Health.cpp

    Return<void> Health::getCapacity(getCapacity_cb _hidl_cb) {
        getProperty<int32_t>(battery_monitor_, BATTERY_PROP_CAPACITY, 0, _hidl_cb);
        return Void();
    }
    

    关联调用的是:
    system\core\healthd\BatteryMonitor.cpp

    status_t BatteryMonitor::getProperty(int id, struct BatteryProperty *val) {
        status_t ret = BAD_VALUE;
        std::string buf;
    
        val->valueInt64 = LONG_MIN;
    
        switch(id) {
    。。。
        case BATTERY_PROP_CAPACITY:
            if (!mHealthdConfig->batteryCapacityPath.isEmpty()) {
                val->valueInt64 =
                    getIntField(mHealthdConfig->batteryCapacityPath);
                ret = OK;
            } else {
                ret = NAME_NOT_FOUND;
            }
            break;
    。。。
        return ret;
    }
    

    healthd服务相关(system\core\healthd ),用于关机充电时获取电池信息的地方。
    void BatteryMonitor::updateValues函数,更新底层上报的电池信息

    void BatteryMonitor::updateValues(void) {
        initHealthInfo(mHealthInfo.get());
    
        HealthInfo_1_0& props = mHealthInfo->legacy.legacy;
    	KLOG_WARNING(LOG_TAG, "BM xmhxj debug :mHealthdConfig->batteryPresentPath.isEmpty() %d\n", mHealthdConfig->batteryPresentPath.isEmpty());
    	KLOG_WARNING(LOG_TAG, "BM xmhxj debug :mHealthdConfig->batteryPresentPath %s\n",mHealthdConfig->batteryPresentPath.string());
    
        if (!mHealthdConfig->batteryPresentPath.isEmpty()){
        	KLOG_WARNING(LOG_TAG, "BM xmhxj debug :!mHealthdConfig->batteryPresentPath.isEmpty() %s\n", mHealthdConfig->batteryPresentPath.string());
    
    		props.batteryPresent = getBooleanField(mHealthdConfig->batteryPresentPath);
        } else {
    
    		props.batteryPresent = mBatteryDevicePresent;
    	KLOG_WARNING(LOG_TAG, "BM xmhxj debug : mHealthdConfig->batteryPresentPath.isEmpty() mBatteryDevicePresent %d\n", mBatteryDevicePresent);
    
        }
    	KLOG_WARNING(LOG_TAG, "BM xmhxj debug : props.batteryPresent %d\n", props.batteryPresent);
    
    	
        props.batteryLevel = mBatteryFixedCapacity ?
            mBatteryFixedCapacity :
            getIntField(mHealthdConfig->batteryCapacityPath);
        props.batteryVoltage = getIntField(mHealthdConfig->batteryVoltagePath) / 1000;
    
        if (!mHealthdConfig->batteryCurrentNowPath.isEmpty())
            props.batteryCurrent = getIntField(mHealthdConfig->batteryCurrentNowPath);
    
        if (!mHealthdConfig->batteryFullChargePath.isEmpty())
            props.batteryFullCharge = getIntField(mHealthdConfig->batteryFullChargePath);
    
        if (!mHealthdConfig->batteryCycleCountPath.isEmpty())
            props.batteryCycleCount = getIntField(mHealthdConfig->batteryCycleCountPath);
    
        if (!mHealthdConfig->batteryChargeCounterPath.isEmpty())
            props.batteryChargeCounter = getIntField(mHealthdConfig->batteryChargeCounterPath);
    
        if (!mHealthdConfig->batteryCurrentAvgPath.isEmpty())
            mHealthInfo->legacy.batteryCurrentAverage =
                    getIntField(mHealthdConfig->batteryCurrentAvgPath);
    
        if (!mHealthdConfig->batteryChargeTimeToFullNowPath.isEmpty())
            mHealthInfo->batteryChargeTimeToFullNowSeconds =
                    getIntField(mHealthdConfig->batteryChargeTimeToFullNowPath);
    
        if (!mHealthdConfig->batteryFullChargeDesignCapacityUahPath.isEmpty())
            mHealthInfo->batteryFullChargeDesignCapacityUah =
                    getIntField(mHealthdConfig->batteryFullChargeDesignCapacityUahPath);
    
        props.batteryTemperature = mBatteryFixedTemperature ?
            mBatteryFixedTemperature :
            getIntField(mHealthdConfig->batteryTemperaturePath);
    
        std::string buf;
    
        if (readFromFile(mHealthdConfig->batteryCapacityLevelPath, &buf) > 0)
            mHealthInfo->batteryCapacityLevel = getBatteryCapacityLevel(buf.c_str());
    
        if (readFromFile(mHealthdConfig->batteryStatusPath, &buf) > 0)
            props.batteryStatus = getBatteryStatus(buf.c_str());
    
        if (readFromFile(mHealthdConfig->batteryHealthPath, &buf) > 0)
            props.batteryHealth = getBatteryHealth(buf.c_str());
    
        if (readFromFile(mHealthdConfig->batteryTechnologyPath, &buf) > 0)
            props.batteryTechnology = String8(buf.c_str());
    
        double MaxPower = 0;
    
        for (size_t i = 0; i < mChargerNames.size(); i++) {
            String8 path;
            path.appendFormat("%s/%s/online", POWER_SUPPLY_SYSFS_PATH,
                              mChargerNames[i].string());
            if (getIntField(path)) {
                path.clear();
                path.appendFormat("%s/%s/type", POWER_SUPPLY_SYSFS_PATH,
                                  mChargerNames[i].string());
                switch(readPowerSupplyType(path)) {
                case ANDROID_POWER_SUPPLY_TYPE_AC:
                    props.chargerAcOnline = true;
                    break;
                case ANDROID_POWER_SUPPLY_TYPE_USB:
                    props.chargerUsbOnline = true;
                    break;
                case ANDROID_POWER_SUPPLY_TYPE_WIRELESS:
                    props.chargerWirelessOnline = true;
                    break;
                default:
                    KLOG_WARNING(LOG_TAG, "%s: Unknown power supply type\n",
                                 mChargerNames[i].string());
                }
                path.clear();
                path.appendFormat("%s/%s/current_max", POWER_SUPPLY_SYSFS_PATH,
                                  mChargerNames[i].string());
                int ChargingCurrent =
                        (access(path.string(), R_OK) == 0) ? getIntField(path) : 0;
    
                path.clear();
                path.appendFormat("%s/%s/voltage_max", POWER_SUPPLY_SYSFS_PATH,
                                  mChargerNames[i].string());
    
                int ChargingVoltage =
                    (access(path.string(), R_OK) == 0) ? getIntField(path) :
                    DEFAULT_VBUS_VOLTAGE;
    
                double power = ((double)ChargingCurrent / MILLION) *
                               ((double)ChargingVoltage / MILLION);
                if (MaxPower < power) {
                    props.maxChargingCurrent = ChargingCurrent;
                    props.maxChargingVoltage = ChargingVoltage;
                    MaxPower = power;
                }
            }
        }
    }
    

    服务初始化函数void BatteryMonitor::init函数:

    void BatteryMonitor::init(struct healthd_config *hc) {  
        String8 path;  
        char pval[PROPERTY_VALUE_MAX];  
    ...  
        mHealthdConfig = hc;  
        std::unique_ptr<DIR, decltype(&closedir)> dir(opendir(POWER_SUPPLY_SYSFS_PATH), closedir);  
        if (dir == NULL) {  
            KLOG_ERROR(LOG_TAG, "Could not open %s\n", POWER_SUPPLY_SYSFS_PATH);  
        } else {  
            struct dirent* entry;  
      
            while ((entry = readdir(dir.get()))) {  
                const char* name = entry->d_name;  
                std::vector<String8>::iterator itIgnoreName;  
                KLOG_WARNING(LOG_TAG, "BM xmhxj debug :INIT 111 name %s\n",name);  
      
                if (!strcmp(name, ".") || !strcmp(name, ".."))  
                    continue;  
      
                itIgnoreName = find(hc->ignorePowerSupplyNames.begin(),  
                                    hc->ignorePowerSupplyNames.end(), String8(name));  
                if (itIgnoreName != hc->ignorePowerSupplyNames.end())  
                    continue;  
                KLOG_WARNING(LOG_TAG, "BM xmhxj debug :INIT 222 name %s\n",name);  
      
                // Look for "type" file in each subdirectory  
                path.clear();  
                path.appendFormat("%s/%s/type", POWER_SUPPLY_SYSFS_PATH, name);  
                KLOG_WARNING(LOG_TAG, "BM xmhxj debug :INIT 333 readPowerSupplyType %d\n",readPowerSupplyType(path));  
      
                switch(readPowerSupplyType(path)) {  
       ...  
      
                case ANDROID_POWER_SUPPLY_TYPE_BATTERY:  
                    KLOG_WARNING(LOG_TAG, "BM xmhxj debug :INIT 333 name %s\n",name);  
      
                    // Some devices expose the battery status of sub-component like  
                    // stylus. Such a device-scoped battery info needs to be skipped  
                    // in BatteryMonitor, which is intended to report the status of  
                    // the battery supplying the power to the whole system.  
                    if (isScopedPowerSupply(name)) continue;  
                    mBatteryDevicePresent = true;  
                    KLOG_WARNING(LOG_TAG, "BM xmhxj debug :INIT 444 name %s\n",name);  
      
                    if (mHealthdConfig->batteryStatusPath.isEmpty()) {  
                        path.clear();  
                        path.appendFormat("%s/%s/status", POWER_SUPPLY_SYSFS_PATH,  
                                          name);  
                        if (access(path, R_OK) == 0)  
                            mHealthdConfig->batteryStatusPath = path;  
                    }  
      
                    if (mHealthdConfig->batteryHealthPath.isEmpty()) {  
                        path.clear();  
                        path.appendFormat("%s/%s/health", POWER_SUPPLY_SYSFS_PATH,  
                                          name);  
                        if (access(path, R_OK) == 0)  
                            mHealthdConfig->batteryHealthPath = path;  
                    }  
                    KLOG_WARNING(LOG_TAG, "BM xmhxj debug :mHealthdConfig->batteryPresentPath %s\n",mHealthdConfig->batteryPresentPath.string());  
      
                    if (mHealthdConfig->batteryPresentPath.isEmpty()) {  
                        path.clear();  
                        path.appendFormat("%s/%s/present", POWER_SUPPLY_SYSFS_PATH,  
                                          name);  
                  
      
                        if (access(path, R_OK) == 0){  
                        mHealthdConfig->batteryPresentPath = path;  
                        KLOG_WARNING(LOG_TAG, "BM xmhxj debug : %s/%s/present ok\n",POWER_SUPPLY_SYSFS_PATH,name);  
      
                        } else {  
                        KLOG_WARNING(LOG_TAG, "BM xmhxj debug : %s/%s/present fail \n",POWER_SUPPLY_SYSFS_PATH,name);  
      
                        }  
      
                    }  
                    KLOG_WARNING(LOG_TAG, "BM xmhxj debug :init batteryPresentPath : %s \n",mHealthdConfig->batteryPresentPath.c_str());  
      
    ...  
      
        // Typically the case for devices which do not have a battery and  
        // and are always plugged into AC mains.  
        if (!mBatteryDevicePresent) {  
            KLOG_WARNING(LOG_TAG, "No battery devices found\n");  
            hc->periodic_chores_interval_fast = -1;  
            hc->periodic_chores_interval_slow = -1;  
        } else {  
    ...  
    }  
    

    vendor\mediatek\proprietary\external\libshowlogo 充电图片显示服务代码
    最终调用void show_battery_capacity(unsigned int capacity)函数为电量显示时调用。


如果你已经解决了该问题, 非常希望你能够分享一下解决方案, 写成博客, 将相关链接放在评论区, 以帮助更多的人 ^-^