mtk INvram服务使用

sancaiodm Android 2023-06-29 453 0

在android 12平台 只有此目录XX:/mnt/vendor/nvdata/APCFG/APRDEB # ls   

BT_Addr  GPS  WIFI  WIFI_CUSTOM

XX:/mnt/vendor/nvdata/APCFG/APRDEB #

网络中所说的/vendor/nvdata/APCFG/APRDEB/是不存在,/mnt/vendor  与/vendor是两个完全不同的目录

/mnt/vendor/nvdata/APCFG/APRDEB/PRODUCT_INFO   //此网络中大部文章都是介绍通过修改此节点从而修改SN号,但博主的项目并没有此节点,应该是android 8.0之后的平台开始就没有此节点,

所以如果平台是高于Android8.0 是无法通过以 INvram.getService()服务以下面两方法来修改SN值 ,因为PRODUCT_INFO 节点都已不存在,

 buff = agent.readFileByName(PRODUCT_INFO_FILENAME, ADDRESS_OFFSET);

int ret = agent.writeFileByNamevec(PRODUCT_INFO_FILENAME, ADDRESS_OFFSET, dataArray);


MTK NVRAM的读写---上层实现SN和MAC读写  [博主按此文章操作,并没有实现对SN值的修改,博主平台是android12,是没有PRODUCT_INFO节点的,只能通过LID方式来修改SN值]



博主自测通过INvram.getService()服务更新wifi mac地址后,通过android api去读wifi mac地址仍是更新前的数据 ,且执行恢复出厂设置节点的值会恢复至修改前的值,

通过INvram.getService()服务更新wifi mac地址再使用flashtool以download only刷入ROM,此时再通过android api去读wifi mac地址则是正常,其中的问题请知道原因的朋友留言指点一下(是否与nvdata写入保护机制有关联),

谢谢


原作出处:Android10.0 压力测试--恢复出厂自动测试工具

如果项目是android.mk文件则如下引用nvram.jar

LOCAL_STATIC_JAVA_LIBRARIES += vendor.mediatek.hardware.nvram-V1.0-java

   public static  String PRODUCT_INFO_FILENAME = "/mnt/vendor/nvdata/APCFG/APRDEB/PRODUCT_INFO";
    private static  void writeData(int n) {
        byte[] write_buff = new byte[]{0, 0, 0, 0};
        byte[] btyeContent = getBytes(n);
        for (int i = 0; i < 4; i++) {
            write_buff[i] = btyeContent[i];
        }
        try {
            INvram agent = INvram.getService();
            if (agent != null) {
                ArrayList<Byte> dataArray = new ArrayList<>(4);
                for (byte b : write_buff) {
                    dataArray.add(new Byte(b));
                }
                int ret = agent.writeFileByNamevec(PRODUCT_INFO_FILENAME, ADDRESS_OFFSET, dataArray);
                if (ret>0){
                    Log.i(TAG,write success"+ ret);
                }else {
                    Log.i(TAG,"write failed"+ ret);
                }
            } else {
                Log.i((TAG, "writeData: agent null");
            }
        } catch (Exception e) {
            Log.e(TAG, "writeData exception:" + e.getLocalizedMessage());
            e.printStackTrace();
        }
    }


    public static  int readData() {
        int targets = 0;
        try {
            String buff = null;
            INvram agent = INvram.getService();
            Log.i(TAG, "readData from PRODUCT_INFO_FILENAME");
            if (agent != null) {
                buff = agent.readFileByName(PRODUCT_INFO_FILENAME, ADDRESS_OFFSET);//10
            }
            byte[] buffArr = HexDump.hexStringToByteArray(buff.substring(0, buff.length() - 1));
            targets = (buffArr[0] & 0xff) | ((buffArr[1] << 8) & 0xff00) | ((buffArr[2] << 24) >>> 8) | (buffArr[3] << 24);
            Log.i(TAG, "readData: buffArr=" + Arrays.toString(buffArr) + ", targets == " + targets);
        } catch (Exception e) {
            Log.e(TAG, "readData exception:" + e.getLocalizedMessage());
            e.printStackTrace();
        }
        return targets;
    }
	

private static  byte[] getBytes(int data) {
        byte[] bytes = new byte[4];
        bytes[0] = (byte) (data & 0xff);
        bytes[1] = (byte) ((data & 0xff00) >> 8);
        bytes[2] = (byte) ((data & 0xff0000) >> 16);
        bytes[3] = (byte) ((data & 0xff000000) >> 24);
        return bytes;
    }

}


【删除写入保护set_write_protect】

vendor\mediatek\proprietary\bootable\bootloader\lk\platform\mt6765\write_protect.c
if (!bypass_wp) {
//set_write_protect(); //注释此行
pal_log_err("write protect Done! \n");
} else
pal_log_err("Bypass write protect! \n");


【3】android10.0(Q) Nvram 新增节点


[4]android10通过nvram读写wifi蓝牙MAC

    final String MAC_WIFI_ADDRESS_FILENAME = "/mnt/vendor/nvdata/APCFG/APRDEB/WIFI";
    final String MAC_BT_ADDRESS_FILENAME = "/mnt/vendor/nvdata/APCFG/APRDEB/BT_Addr";
    final int MAC_WIFI_ADDRESS_OFFSET = 4;
    final int MAC_BT_ADDRESS_OFFSET = 0;
    final int MAC_ADDRESS_DIGITS = 6;
    
public String getMacAddr(String file, int offset, int size) {
        Log.d(TAG, "getMacAddress(): start");

        StringBuffer nvramBuf = new StringBuffer();
        try {
            int i = 0;
            String buff = null;
            INvram agent = INvram.getService();
            if (agent == null) {
                Log.e(TAG, "NvRAMAgent is null");
            }
            try {
                buff = agent.readFileByName(file, offset + size);
            } catch (Exception e) {
                e.printStackTrace();
            }
            Log.i(TAG, "Raw data:" + buff);
            if (buff.length() < 2 * (offset + size)) {
            }
            // Remove the \0 special character.
            int macLen = buff.length() - 1;
            for (i = offset * 2; i < macLen; i += 2) {
                if ((i + 2) < macLen) {
                    nvramBuf.append(buff.substring(i, i + 2));
                    nvramBuf.append(":");
                } else {
                    nvramBuf.append(buff.substring(i));
                }
            }
            Log.d(TAG, "buff:" + nvramBuf.toString());

        } catch (RemoteException re) {
            re.printStackTrace();

        } catch (IndexOutOfBoundsException iobe) {
            iobe.printStackTrace();

        } finally {
            Log.d(TAG, "getMacAddress(): end");
        }

        return nvramBuf.toString();
    }

    private void updateMacAddr(String file, String mac, int offset, int size) {//此方法对WIFI,BT的更新都适用,支持动态移位
        try {
            int i = 0;
            INvram agent = INvram.getService();
            byte[] macAddr = new byte[size];
            if (agent == null) {
                Log.e(TAG, "NvRAMAgent is null");
                return;
            }

            //parse mac address firstly
            StringTokenizer txtBuffer = new StringTokenizer(mac, ":");
            while (txtBuffer.hasMoreTokens()) {
                macAddr[i] = (byte) Integer.parseInt(txtBuffer.nextToken(), 16);
                i++;
            }
            if (i != size) {
                Log.e(TAG, "Wrong length of macAddr:" + i);
                Log.d(TAG, "The format of mac address is not correct");
                return;
            }

            String buff = null;
            try {
                buff = agent.readFileByName(file, offset + size);
            } catch (Exception e) {
                e.printStackTrace();
                return;
            }

            // Remove \0 in the end
            byte[] buffArr = HexDump.hexStringToByteArray(buff.substring(0, buff.length() - 1));

            for (i = 0; i < size; i ++) {
                Log.e(TAG, "i:" + i);
                Log.e(TAG, "size:" + size);
                if(file.equals(MAC_WIFI_ADDRESS_FILENAME))
                    buffArr[i + MAC_WIFI_ADDRESS_OFFSET] = macAddr[i];
                else if(file.equals(MAC_BT_ADDRESS_FILENAME))
                    buffArr[i + MAC_BT_ADDRESS_OFFSET] = macAddr[i];
                else {
                    Log.e(TAG, "Wrong file of name:" + file);
                    return;
                }

            }

            ArrayList<Byte> dataArray = new ArrayList<Byte>(offset + size);

            for (i = 0; i < offset + size; i++) {
                dataArray.add(i, new Byte(buffArr[i]));
            }

            int flag = 0;
            try {
                flag = agent.writeFileByNamevec(file, offset + size, dataArray);
            } catch (Exception e) {
                e.printStackTrace();
                Log.d(TAG, e.getMessage() + ":" + e.getCause());
                return;
            }
            Log.d(TAG, "Update successfully.\r\nPlease reboot this device");
        } catch (Exception e) {
            Log.d(TAG,e.getMessage() + ":" + e.getCause());
            e.printStackTrace();
        }
    }
}


评论