其他分享
首页 > 其他分享> > 20210408-学习随笔

20210408-学习随笔

作者:互联网

20210408-学习随笔

DEX文件结构

dex文件整体结构

结构名称 解释
dex header dex文件头部,记录整个dex文件的相关属性
string_ids 字符串数据索引,记录了每个字符串的偏移量
type_ids 数据类型数组,记录了每个类型在string_ids数组中的的字符串索引
proto_ids 方法声明的偏移量,记录了方法声明的字符串,返回类型字符串,参数列表
field_ids 字段数据索引,记录了所属类,类型以及方法名
method_ids 类方法索引,记录方法所属类名,方法声明以及方法名等信息
class_defs 类定义数据索引,记录指定类各类信息,包括接口,超类,类数据偏移量
data 数据区,保存了各个类的真实数据
link_data 静态链接数据区

dex header

struct DexHeader {
    u1  magic[8];           /* 版本标识 */
    u4  checksum;           /* adler32 检验 */
    u1  signature[kSHA1DigestLen]; /* SHA-1 哈希值 */
    u4  fileSize;           /* 整个文件大小 */
    u4  headerSize;         /* DexHeader 大小 */
    u4  endianTag;          /* 字节序标记 */
    u4  linkSize;           /* 链接段大小 */
    u4  linkOff;            /* 链接段偏移 */
    u4  mapOff;             /* DexMapList 的文件偏移 */
    u4  stringIdsSize;      /* DexStringId 的个数 */
    u4  stringIdsOff;       /* DexStringId 的文件偏移 */
    u4  typeIdsSize;        /* DexTypeId 的个数 */
    u4  typeIdsOff;         /* DexTypeId 的文件偏移 */
    u4  protoIdsSize;       /* DexProtoId 的个数 */
    u4  protoIdsOff;        /* DexProtoId 的文件偏移 */
    u4  fieldIdsSize;       /* DexFieldId 的个数 */
    u4  fieldIdsOff;        /* DexFieldId 的文件偏移 */
    u4  methodIdsSize;      /* DexMethodId 的个数 */
    u4  methodIdsOff;       /* DexMethodId 的文件偏移 */
    u4  classDefsSize;      /* DexClassDef 的个数 */
    u4  classDefsOff;       /* DexClassDef 的文件偏移 */
    u4  dataSize;           /* 数据段的大小 */
    u4  dataOff;            /* 数据段的文件偏移 */
};

string_ids

存放字符串所在位置的偏移

其中字符串第一个字节保存着字符串的长度,之后是一个char数组,以00结尾

type_ids

是用到的类型数组,每个元素为用到的类型(类),存放的数据为在string_ids数组中的索引

proto_ids

方法原型声明的数组

struct DexProtoId {
    u4 shortyIdx;		// 返回类型 string_ids 的索引
    u4 returnTypeIdx;	// 返回类型 type_ids 的索引
    u4 parametersOff;	/* 指向参数类型列表的文件偏移量
    没有参数则为0 非0则指向的数据应满足type_item格式*/
}

field_ids

struct filed_id_item{
  ushort class_idx;		// 字段所属的class type_ids的索引
  ushort type_idx;		// 字段的类型 type_ids的索引
  uint name_idx;		// 字段的名称 string_ids的索引
}

method_ids

struct method_id_item{
  ushort class_idx;		// 方法所属的class type_ids的索引
  ushort proto_idx;		// 方法的原型 proto_ids的索引
  uint name_idx;		// 方法的名称 string_ids的索引
}

class_defs

struct class_def_item {
  uint class_idx;			// 类的类型,type_ids的索引
  uint access_flags; 		// 访问标志
  uint superclass_idx; 		// 父类类型 type_ids的索引
  uint interfaces_off;		// 接口 之想type_list的偏移,没有为0
  uint source_file_idx; 	// 源文件名 string_ids的索引
  uint annotations_off; 	// 注解
  uint class_data_off; 		// 指向 class_data结构的文件偏移
  uint static_value_off;	// 
}

struct class_data_item{
  uleb128 static_fields_size;     //静态字段
  uleb128 instance_fields_size;   //实例字段
  uleb128 direct_methods_size;    //直接方法(private或者构造方法)
  uleb128 virtual_methods_size;   //虚方法(非private、static、final,非构造方法)
  encoded_field static_fields[static_fields_size];        //静态字段
  encoded_field instance_fields[instance_fields_size];    //实例字段
  encoded_method direct_methods[direct_method_size];      //直接方法
  encoded_method virtual_methods[virtual_methods_size];   //虚方法
}

struct encoded_field{
  uleb128 filed_idx_diff;
  uleb128 access_flags;
}

struct encoded_method{
  uleb128 method_idx_diff;	// method_ids的索引
  uleb128 access_flags;		// 访问权限
  uleb128 code_off;			// 本方法的代码实现,指向data区
}

map_list

// map_list 结构
struct DexMapList {
    u4 size;			// DexMapItem结构的个数
    DexMapItem list[l];	// DexMapItem结构
}

size表明 DexMapItem结构的个数

struct DexMapItem {
    u2 type;		// 整体结构中的结构类型
    u2 unused;		// 用于字节对齐
    u4 size;		// 类型的个数
    u4 offset;		// 类型数据的文件偏移
}

Q&A

安装APK报错Failure [INSTALL_FAILED_TEST_ONLY]

安装APK报错Failure [INSTALL_FAILED_TEST_ONLY]

安装失败!调用者不被允许测试的测试程序

修改AndroidManifest.xml

application标签中删去 android:testOnly="true"属性

AndroidStudio使用smaliidea

安装smaliidea插件后

然后在Android Studio -> Preference(windows是File -> setting) -> Editor -> file Types 里面找smali,给图标为【黑色S】的smali添加.smali,去掉自带的smali的.smali

标签:20210408,idx,u4,ids,学习,索引,偏移,随笔,type
来源: https://www.cnblogs.com/Forgo7ten/p/14643172.html