Exemple #1
0
def encodeutf(string):
    str_data = []
    str_count = 0
    if config.get_value('XMLFLAG') == 0:
        str_data.append(hex(len(string)))
        str_data.append(hex(0))
        for str_i in string:
            encod_str = hex(ord(str_i.encode("utf-8")))
            str_data.append(encod_str)
            str_data.append(hex(0))
        str_data.append(hex(0))
        str_data.append(hex(0))
    elif config.get_value('XMLFLAG') == 1:
        #此时为XML资源文件格式
        str_data.append(hex(len(string)))
        str_data.append(hex(len(string)))
        for str_i in string:
            encod_str = hex(ord(str_i.encode("utf-8")))
            str_data.append(encod_str)
        str_data.append(hex(0))
        #和4倍对齐,所以最多循环3次
        for i in range(3):
            if (str_count + 1 + 2) % 4 == 0:
                return str_data
            else:
                str_count += 1
                str_data.append(hex(0))
    # print str_data
    return str_data
Exemple #2
0
def am_resourceidchunk(data, pc):
    # ChunkType:ResourceId Chunk类型,固定四个字节0x00080180
    ChunkType = ApUtils.little_endian(data[pc:pc + 4])
    if ApUtils.printhex(ChunkType) == "0x00080180":
        ApUtils.apprint("===========Resolve ResourceId Chunk=============")
        ApUtils.apprint("[Resource]ChunkType is : " +
                        ApUtils.printhex(ChunkType))
    else:
        ApUtils.apprint("[Error]ResourceId Chunk resolve error!")
        exit(-1)

    # ResourceId Chunk的大小(4)
    ChunkSize = ApUtils.little_endian(data[pc + 4:pc + 8])
    ApUtils.apprint("[Resource]ChunkSize is : " + ApUtils.printhex(ChunkSize))

    # ResourcesId的个数为(大小-头部8字节)/4
    ResourcesId_num = int((int(ApUtils.printhex(ChunkSize), 16) - 8) / 4)
    for i in range(ResourcesId_num):
        tmp_hex = ApUtils.printhex(
            ApUtils.little_endian(data[pc + 8 + i * 4:pc + 8 + i * 4 + 4]))
        tmp = int(tmp_hex, 16)
        ApUtils.apprint("[Resource][" + str(i) + "]Id : " + str(tmp) +
                        ",hex : " + tmp_hex)
        config.global_list['RESOURCEIDS'].append(tmp_hex)

    config.set_value(
        'RESOURCEIDCHUNKEND',
        config.get_value('RESOURCEIDCHUNKSTAR') +
        int(ApUtils.printhex(ChunkSize), 16))
Exemple #3
0
def am_tagchunk_end(data, pc):
    # ChunkType:end Tag Chunk类型,固定四个字节0x00100103
    ChunkType = ApUtils.little_endian(data[pc:pc + 4])
    if ApUtils.printhex(ChunkType) == "0x00100103":
        ApUtils.apprint(" ===========Resolve Tag Chunk End=============")
        ApUtils.apprint(" [endTag" + str(config.get_value('TAGCOUNTEND')) +
                        "]ChunkType is : " + ApUtils.printhex(ChunkType))
    else:
        ApUtils.apprint(" [Error" + str(config.get_value('TAGCOUNTEND')) +
                        "]Tag Chunk end resolve error!")
        exit(-1)

    # Tag Chunk的大小(4)
    ChunkSize = ApUtils.little_endian(data[pc + 4:pc + 8])
    ApUtils.apprint(" [endTag" + str(config.get_value('TAGCOUNTEND')) +
                    "]ChunkSize is : " + ApUtils.printhex(ChunkSize))

    # Line Number 行号(4)
    LineNumber = ApUtils.little_endian(data[pc + 8:pc + 12])
    ApUtils.apprint(" [endTag" + str(config.get_value('TAGCOUNTEND')) +
                    "]LineNumber is : " + ApUtils.printhex(LineNumber))

    # Unknown未知区域(4)
    Unknown = ApUtils.little_endian(data[pc + 12:pc + 16])

    # Namespace Uri
    NameSpcae = ApUtils.little_endian(data[pc + 16:pc + 20])
    if int(ApUtils.printhex(NameSpcae), 16) <= len(
            config.global_list['STRINGPOOL']):
        ApUtils.apprint(" [endTag" + str(config.get_value('TAGCOUNTEND')) +
                        "]NameSpace is : " + config.global_list['STRINGPOOL'][
                            int(ApUtils.printhex(NameSpcae), 16)])
    else:
        ApUtils.apprint(" [endTag" + str(config.get_value('TAGCOUNTEND')) +
                        "]NameSpace is : null")

    # name
    Name = ApUtils.little_endian(data[pc + 20:pc + 24])
    NameStr = config.global_list['STRINGPOOL'][int(ApUtils.printhex(Name), 16)]
    ApUtils.apprint(" [endTag" + str(config.get_value('TAGCOUNTEND')) +
                    "]Tag name is : " + NameStr)

    # 修改结束指针
    config.set_value(
        'ENDTAGCHUNKEND',
        config.get_value('ENDTAGCHUNKSTAR') +
        int(ApUtils.printhex(ChunkSize), 16))
Exemple #4
0
def am_namespacechunk_star(data, pc):
    # ChunkType:Namespace Chunk类型,固定四个字节0x00100100
    ChunkType = ApUtils.little_endian(data[pc:pc + 4])
    if ApUtils.printhex(ChunkType) == "0x00100100":
        ApUtils.apprint(
            "===========Resolve Namespace Chunk Start=============")
        ApUtils.apprint("[startNamespace]ChunkType is : " +
                        ApUtils.printhex(ChunkType))
    else:
        ApUtils.apprint("[Error]Namespace Chunk Start resolve error!")
        exit(-1)

    # Namespace Chunk的大小(4)
    ChunkSize = ApUtils.little_endian(data[pc + 4:pc + 8])
    ApUtils.apprint("[startNamespace]ChunkSize is : " +
                    ApUtils.printhex(ChunkSize))

    # Line Number 行号(4)
    LineNumber = ApUtils.little_endian(data[pc + 8:pc + 12])
    ApUtils.apprint("[startNamespace]LineNumber is : " +
                    ApUtils.printhex(LineNumber))

    # Unknown未知区域(4)
    Unknown = ApUtils.little_endian(data[pc + 12:pc + 16])

    # Prefix命名空间前缀(4)(字符串索引)
    Prefix = ApUtils.little_endian(data[pc + 16:pc + 20])
    PrefixName = config.global_list['STRINGPOOL'][int(ApUtils.printhex(Prefix),
                                                      16)]
    ApUtils.apprint("[startNamespace]Prefix is : " + ApUtils.printhex(Prefix) +
                    " , str is : " + PrefixName)

    # Uri命名空间的URI(4)(字符串索引)
    Url = ApUtils.little_endian(data[pc + 20:pc + 24])
    UrlName = config.global_list['STRINGPOOL'][int(ApUtils.printhex(Url), 16)]
    ApUtils.apprint("[startNamespace]Url is : " + ApUtils.printhex(Url) +
                    " , str is : " + UrlName)

    config.set_value(
        'STARNAMESPACEEND',
        config.get_value('STARNAMESPACESTAR') +
        int(ApUtils.printhex(ChunkSize), 16))
Exemple #5
0
def am_textchunk(data, pc):
    # ChunkType:text chunk 类型,固定四个字节0x00100104
    ChunkType = ApUtils.little_endian(data[pc:pc + 4])
    if ApUtils.printhex(ChunkType) == "0x00100104":
        ApUtils.apprint(" ===========Resolve Text Chunk=============")
        ApUtils.apprint(" [textChunk]" + ApUtils.printhex(ChunkType))
    else:
        ApUtils.apprint(" [Error]Text Chunk resolve error!")
        exit(-1)

    # Tag Chunk的大小(4)
    ChunkSize = ApUtils.little_endian(data[pc + 4:pc + 8])
    ApUtils.apprint(" [textChunk]ChunkSize is : " +
                    ApUtils.printhex(ChunkSize))

    # Line Number 行号(4)
    LineNumber = ApUtils.little_endian(data[pc + 8:pc + 12])
    ApUtils.apprint(" [textChunk]LineNumber is : " +
                    ApUtils.printhex(LineNumber))

    # Unknown未知区域(4)
    Unknown = ApUtils.little_endian(data[pc + 12:pc + 16])

    # nameApUtils
    Name = ApUtils.little_endian(data[pc + 16:pc + 20])
    NameStr = config.global_list['STRINGPOOL'][int(ApUtils.printhex(Name), 16)]
    ApUtils.apprint(" [textChunk]Text name is : " + NameStr)

    # Unknown未知区域(4)
    Unknown1 = ApUtils.little_endian(data[pc + 20:pc + 24])

    # Unknown未知区域(4)
    Unknown2 = ApUtils.little_endian(data[pc + 24:pc + 28])

    config.set_value(
        'TEXTCHUNKEND',
        config.get_value('TEXTCHUNKSTAR') +
        int(ApUtils.printhex(ChunkSize), 16))
Exemple #6
0
def am_stringchunk(data, pc):
    # StringChunk的类型,固定4个字节
    ChunkType = ApUtils.little_endian(data[pc:pc + 4])
    if ApUtils.printhex(ChunkType) == "0x001c0001":
        ApUtils.apprint("===========Resolve String Chunk=============")
        ApUtils.apprint("[String]ChunkType is : " +
                        ApUtils.printhex(ChunkType))
    else:
        ApUtils.apprint("[Error]String Chunk resolve error!")
        exit(-1)

    # StringChunk的大小(4)
    ChunkSize = ApUtils.little_endian(data[pc + 4:pc + 8])
    ApUtils.apprint("[String]ChunkSize is : " + ApUtils.printhex(ChunkSize))
    config.set_value('STRINGCHUNKSIZEINDEX', pc + 4)

    # StringChunk中字符串的个数(4)
    StringCount = ApUtils.little_endian(data[pc + 8:pc + 12])
    ApUtils.apprint("[String]StringCount is : " +
                    ApUtils.printhex(StringCount))
    config.set_value('STRINGCHUNKCOUNTINDEX', pc + 8)

    # StringChunk中样式的个数(4)
    StyleCount = ApUtils.little_endian(data[pc + 12:pc + 16])
    ApUtils.apprint("[String]StyleCount is : " + ApUtils.printhex(StyleCount))

    # Unknown(4)
    Unknown = ApUtils.little_endian(data[pc + 16:pc + 20])
    #如果此时Unknown为0x00010000也就是256,说明此时使用的为xml编码格式
    if int(ApUtils.printhex(Unknown), 16) == 256:
        ApUtils.apprint("[String]This is XML Flag!")
        config.set_value('XMLFLAG', 1)

    # 字符串池的偏移值(4)
    StringPoolOffset = ApUtils.little_endian(data[pc + 20:pc + 24])
    ApUtils.apprint("[String]StringPoolOffset is : " +
                    ApUtils.printhex(StringPoolOffset))
    config.set_value('STRINGPOOLOFFSET', StringPoolOffset)
    config.set_value('STRINGPOOLOFFSETINDEX', pc + 20)

    # 样式池的偏移值(4)
    StylePoolOffset = ApUtils.little_endian(data[pc + 24:pc + 28])
    ApUtils.apprint("[String]StylePoolOffset is : " +
                    ApUtils.printhex(StylePoolOffset))
    config.set_value('STYLEPOOLOFFSET', StylePoolOffset)

    # 每个字符串的偏移
    if int(ApUtils.printhex(StringCount), 16) != 0:
        StringOffsets = []
        for i in range(int(ApUtils.printhex(StringCount), 16)):
            StringOffset = ApUtils.little_endian(data[pc + 28 + i * 4:pc + 28 +
                                                      i * 4 + 4])
            StringOffsets.append(StringOffset)
            config.set_value('LASTSTRINGOFFSETSINDEX', pc + 28 + i * 4)
        # 每个字符串的偏移列表
        config.global_list['STRINGOFFSETS'].extend(StringOffsets)
    else:
        ApUtils.apprint("[String]There is no String")

    # 每个样式的偏移
    if int(ApUtils.printhex(StyleCount), 16) != 0:
        StyleOffsets = []
        for j in range(int(ApUtils.printhex(StyleCount), 16)):
            StyleOffset = ApUtils.little_endian(
                data[pc + 28 + int(ApUtils.printhex(StringCount), 16) * 4 +
                     j * 4:pc + 28 +
                     int(ApUtils.printhex(StringCount), 16) * 4 + j * 4 + 4])
            StyleOffsets.append(StyleOffset)
        # 每个字符串的偏移列表
        config.global_list['STYLEOFFSETS'].extend(StyleOffsets)
    else:
        ApUtils.apprint("[String]There is no Style")

    # =======开始解析字符串===========#
    count = 0
    if config.get_value('XMLFLAG') == 0:
        for index in config.global_list['STRINGOFFSETS']:
            str_index = pc + int(
                ApUtils.printhex(config.get_value('STRINGPOOLOFFSET')),
                16) + int(ApUtils.printhex(index), 16)
            str_len = int(
                ApUtils.printhex(
                    ApUtils.little_endian(data[str_index:str_index + 2])), 16)
            str_end = data[str_index + (str_len + 1) * 2:str_index +
                           (str_len + 1) * 2 + 2]
            # utf-8编码
            try:
                string = ApUtils.read_asc(data[str_index + 2:str_index + 2 + str_len * 2])\
                    .encode("utf-8").decode('unicode_escape')
            except:
                try:
                    string = ApUtils.read_asc(data[str_index + 2:str_index + 2 + str_len * 2])\
                        .encode("utf-8").decode('unicode_escape')
                except:
                    string = "String resolve error !!"
            config.set_value('STRINGCHUNKEND', str_index + 2 + str_len * 2 + 2)
            ApUtils.apprint(" [StringPool][" + str(count) + "]" + string)
            config.global_list['STRINGPOOL'].append(string)
            count += 1
            config.set_value('LASTSTRINGLEN', str_len)
        config.set_value('LASTSTRINGINDEX', config.get_value('STRINGCHUNKEND'))
    elif config.get_value('XMLFLAG') == 1:
        for index in config.global_list['STRINGOFFSETS']:
            str_index = pc + int(
                ApUtils.printhex(config.get_value('STRINGPOOLOFFSET')),
                16) + int(ApUtils.printhex(index), 16)
            str_len = int(
                ApUtils.printhex(
                    ApUtils.little_endian(data[str_index + 1:str_index + 2])),
                16)
            # utf-8编码
            try:
                string = ApUtils.read_asc(data[str_index + 2:str_index + 2 + str_len ])\
                    .encode("utf-8").decode('unicode_escape')
            except:
                try:
                    string = ApUtils.read_asc(data[str_index + 2:str_index + 2 + str_len])\
                        .encode("utf-8").decode('unicode_escape')
                except:
                    string = "String resolve error !!"
            config.set_value('STRINGCHUNKEND', str_index + 2 + str_len + 1)
            ApUtils.apprint(" [StringPool][" + str(count) + "]" + string)
            config.global_list['STRINGPOOL'].append(string)
            count += 1
            config.set_value('LASTSTRINGLEN', str_len)
        config.set_value('LASTSTRINGINDEX', config.get_value('STRINGCHUNKEND'))
    else:
        ApUtils.apprint("[String]XMLFLAG is Wrong!")
        exit(-1)
Exemple #7
0
def am_tagchunk_star(data, pc):
    # ChunkType:Tag Chunk类型,固定四个字节0x00100102
    ChunkType = ApUtils.little_endian(data[pc:pc + 4])
    if ApUtils.printhex(ChunkType) == "0x00100102":
        ApUtils.apprint(" ===========Resolve Tag Chunk Start=============")
        ApUtils.apprint(" [startTag" + str(config.get_value('TAGCOUNTSTAR')) +
                        "]ChunkType is : " + ApUtils.printhex(ChunkType))
    else:
        ApUtils.apprint(" [Error" + str(config.get_value('TAGCOUNTSTAR')) +
                        "]Tag Chunk start resolve error!")
        exit(-1)

    # Tag Chunk的大小(4)
    ChunkSize = ApUtils.little_endian(data[pc + 4:pc + 8])
    ApUtils.apprint(" [startTag" + str(config.get_value('TAGCOUNTSTAR')) +
                    "]ChunkSize is : " + ApUtils.printhex(ChunkSize))

    # Line Number 行号(4)
    LineNumber = ApUtils.little_endian(data[pc + 8:pc + 12])
    ApUtils.apprint(" [startTag" + str(config.get_value('TAGCOUNTSTAR')) +
                    "]LineNumber is : " + ApUtils.printhex(LineNumber))

    # Unknown未知区域(4)
    Unknown = ApUtils.little_endian(data[pc + 12:pc + 16])

    # Namespace Uri
    NameSpcae = ApUtils.little_endian(data[pc + 16:pc + 20])
    if int(ApUtils.printhex(NameSpcae), 16) <= len(
            config.global_list['STRINGPOOL']):
        ApUtils.apprint(" [startTag" + str(config.get_value('TAGCOUNTSTAR')) +
                        "]NameSpace is : " + config.global_list['STRINGPOOL'][
                            int(ApUtils.printhex(NameSpcae), 16)])
    else:
        ApUtils.apprint(" [startTag" + str(config.get_value('TAGCOUNTSTAR')) +
                        "]NameSpace is : null")

    # name
    Name = ApUtils.little_endian(data[pc + 20:pc + 24])
    NameStr = config.global_list['STRINGPOOL'][int(ApUtils.printhex(Name), 16)]
    ApUtils.apprint(" [startTag" + str(config.get_value('TAGCOUNTSTAR')) +
                    "]Tag name is : " + NameStr)
    if NameStr == "application":
        config.set_value('APPLICATIONPC', pc)

    # Flags好像没有意义,一般都是0x00140014
    Flags = ApUtils.little_endian(data[pc + 24:pc + 28])

    # Attribute Count
    AttributeCount = ApUtils.little_endian(data[pc + 28:pc + 32])
    ApUtils.apprint(" [startTag" + str(config.get_value('TAGCOUNTSTAR')) +
                    "]Attribute Count is : " +
                    ApUtils.printhex(AttributeCount))

    # Class Attribute一般也没用,0x00000000
    ClassAttibute = ApUtils.little_endian(data[pc + 32:pc + 36])

    # Attributes
    for i in range(int(ApUtils.printhex(AttributeCount), 16)):
        att_namespace = ApUtils.little_endian(data[pc + 36 + i * 5 * 4:pc +
                                                   36 + i * 5 * 4 + 4])
        att_name = ApUtils.little_endian(data[pc + 36 + i * 5 * 4 + 4:pc + 36 +
                                              i * 5 * 4 + 4 + 4])
        att_valuestr = ApUtils.little_endian(
            data[pc + 36 + i * 5 * 4 + 4 + 4:pc + 36 + i * 5 * 4 + 4 + 4 + 4])
        att_type = ApUtils.little_endian(
            data[pc + 36 + i * 5 * 4 + 4 + 4 + 4:pc + 36 + i * 5 * 4 + 4 + 4 +
                 4 + 4])
        att_data = ApUtils.little_endian(
            data[pc + 36 + i * 5 * 4 + 4 + 4 + 4 + 4:pc + 36 + i * 5 * 4 + 4 +
                 4 + 4 + 4 + 4])
        # 打印
        #print(" ----------------------------------------------")
        if int(ApUtils.printhex(att_namespace), 16) <= len(
                config.global_list['STRINGPOOL']):
            ApUtils.apprint("     [startTag" +
                            str(config.get_value('TAGCOUNTSTAR')) +
                            "]Attribute[" + str(i) + "]NameSpace is : " +
                            config.global_list['STRINGPOOL'][int(
                                ApUtils.printhex(att_namespace), 16)])
        else:
            ApUtils.apprint("     [startTag" +
                            str(config.get_value('TAGCOUNTSTAR')) +
                            "]Attribute[" + str(i) + "]NameSpace is null ")

        if int(ApUtils.printhex(att_name), 16) <= len(
                config.global_list['STRINGPOOL']):
            attr_name = config.global_list['STRINGPOOL'][int(
                ApUtils.printhex(att_name), 16)]
            ApUtils.apprint("     [startTag" +
                            str(config.get_value('TAGCOUNTSTAR')) +
                            "]Attribute[" + str(i) + "]Name is : " + attr_name)
            # 修改application name
            if NameStr == "application":
                if attr_name == "name":
                    config.set_value('APPLICATIONNAMEFLAG', 1)
                    config.set_value('APPLICATIONNAMEINDEX',
                                     pc + 36 + i * 5 * 4)
        else:
            ApUtils.apprint("     [startTag" +
                            str(config.get_value('TAGCOUNTSTAR')) +
                            "]Attribute[" + str(i) + "]Name is null ")

        if int(ApUtils.printhex(att_valuestr), 16) <= len(
                config.global_list['STRINGPOOL']):
            ApUtils.apprint("     [startTag" +
                            str(config.get_value('TAGCOUNTSTAR')) +
                            "]Attribute[" + str(i) + "]Valus String is : " +
                            config.global_list['STRINGPOOL'][int(
                                ApUtils.printhex(att_valuestr), 16)])
        else:
            ApUtils.apprint("     [startTag" +
                            str(config.get_value('TAGCOUNTSTAR')) +
                            "]Attribute[" + str(i) + "]Valus String is null ")

        type = ApUtils.getAttrType(int(ApUtils.printhex(att_type), 16) >> 24)
        ApUtils.apprint("     [startTag" +
                        str(config.get_value('TAGCOUNTSTAR')) + "]Attribute[" +
                        str(i) + "]Type is : " + type)

        dataAtt = ApUtils.getAttrData(
            int(ApUtils.printhex(att_type), 16) >> 24, att_data)
        ApUtils.apprint("     [startTag" +
                        str(config.get_value('TAGCOUNTSTAR')) + "]Attribute[" +
                        str(i) + "]Data is : " + dataAtt)
    # 修改结束指针
    config.set_value(
        'STARTTAGCHUNKEND',
        config.get_value('STARTTAGCHUNKSTAR') +
        int(ApUtils.printhex(ChunkSize), 16))
Exemple #8
0
def changeApplication(source_filepath, target_filepath, application_name):
    # 用于存储修改之后的AM文件
    cp_data = []

    # 解析AM文件
    data_hex = resolver(source_filepath)
    print("[ApEditor]Begin to change application")

    # 解析要修改的字符串
    data_string = ApUtils.encodeutf(application_name)

    # 处理头部
    cp_data.extend(data_hex[0:config.get_value('FILSIZEINDEX')])
    # file size
    old_filesize = ApUtils.printhex(
        ApUtils.little_endian(
            data_hex[config.get_value('FILSIZEINDEX'
                                      ):config.get_value('FILSIZEINDEX') + 4]))
    new_filesize = int(old_filesize, 16) + 4 + len(data_string)
    if config.get_value('APPLICATIONNAMEFLAG') == 0:
        # 此时需要新加application中name属性
        new_filesize += 5 * 4
    cp_data.extend(ApUtils.encodehex(new_filesize))

    cp_data.extend(data_hex[config.get_value('FILSIZEINDEX') +
                            4:config.get_value('STRINGCHUNKSIZEINDEX')])
    # String chunk size
    old_stringchunk_size = ApUtils.printhex(
        ApUtils.little_endian(
            data_hex[config.get_value('STRINGCHUNKSIZEINDEX'):config.
                     get_value('STRINGCHUNKSIZEINDEX') + 4]))
    new_stringchunk_size = int(old_stringchunk_size, 16) + 4 + len(data_string)
    cp_data.extend(ApUtils.encodehex(new_stringchunk_size))

    cp_data.extend(data_hex[config.get_value('STRINGCHUNKSIZEINDEX') +
                            4:config.get_value('STRINGCHUNKCOUNTINDEX')])
    # String chunk count
    old_stringchunk_count = ApUtils.printhex(
        ApUtils.little_endian(
            data_hex[config.get_value('STRINGCHUNKCOUNTINDEX'):config.
                     get_value('STRINGCHUNKCOUNTINDEX') + 4]))
    new_stringchunk_count = int(old_stringchunk_count, 16) + 1
    cp_data.extend(ApUtils.encodehex(new_stringchunk_count))

    cp_data.extend(data_hex[config.get_value('STRINGCHUNKCOUNTINDEX') +
                            4:config.get_value('STRINGPOOLOFFSETINDEX')])
    # Stringpool off set
    old_stringpool_offset = ApUtils.printhex(
        ApUtils.little_endian(
            data_hex[config.get_value('STRINGPOOLOFFSETINDEX'):config.
                     get_value('STRINGPOOLOFFSETINDEX') + 4]))
    new_stringpool_offset = int(old_stringpool_offset, 16) + 4
    cp_data.extend(ApUtils.encodehex(new_stringpool_offset))

    # String off sets
    cp_data.extend(data_hex[config.get_value('STRINGPOOLOFFSETINDEX') +
                            4:config.get_value('LASTSTRINGOFFSETSINDEX') + 4])
    old_laststring_offsets = ApUtils.printhex(
        ApUtils.little_endian(
            data_hex[config.get_value('LASTSTRINGOFFSETSINDEX'):config.
                     get_value('LASTSTRINGOFFSETSINDEX') + 4]))
    if config.get_value('XMLFLAG') == 0:
        new_laststring_offsets = int(
            old_laststring_offsets,
            16) + (config.get_value('LASTSTRINGLEN') + 2) * 2
        cp_data.extend(ApUtils.encodehex(new_laststring_offsets))
    elif config.get_value('XMLFLAG') == 1:
        new_laststring_offsets = int(old_laststring_offsets, 16) + (
            config.get_value('LASTSTRINGLEN') + 2 + 1)
        cp_data.extend(ApUtils.encodehex(new_laststring_offsets))
    else:
        print "[Error]Something wrong with XMLFLAG!"
        exit(-1)

    cp_data.extend(data_hex[config.get_value('LASTSTRINGOFFSETSINDEX') +
                            4:config.get_value('LASTSTRINGINDEX')])
    # sting
    cp_data.extend(data_string)

    # 修改applicaiton name
    if config.get_value('APPLICATIONNAMEFLAG') == 1:
        # 此时application中含有android:name属性,直接修改字符串指针即可
        cp_data.extend(data_hex[config.get_value('LASTSTRINGINDEX'):config.
                                get_value('APPLICATIONNAMEINDEX')])
        # namespace不用换
        cp_data.extend(
            data_hex[config.get_value('APPLICATIONNAMEINDEX'):config.
                     get_value('APPLICATIONNAMEINDEX') + 4])
        # name不换
        cp_data.extend(
            data_hex[config.get_value('APPLICATIONNAMEINDEX') +
                     4:config.get_value('APPLICATIONNAMEINDEX') + 4 + 4])
        # valuesstr换,这里是下标,从0开始,因此-1
        cp_data.extend(ApUtils.encodehex(new_stringchunk_count - 1))
        # type不换
        cp_data.extend(
            data_hex[config.get_value('APPLICATIONNAMEINDEX') + 4 + 4 +
                     4:config.get_value('APPLICATIONNAMEINDEX') + 4 + 4 + 4 +
                     4])
        # data换
        cp_data.extend(ApUtils.encodehex(new_stringchunk_count - 1))

        cp_data.extend(data_hex[config.get_value('APPLICATIONNAMEINDEX') + 4 +
                                4 + 4 + 4 + 4:])
    elif config.get_value('APPLICATIONNAMEFLAG') == 0:
        # 此时application中没有android:name属性,新增一个属性
        cp_data.extend(data_hex[config.get_value('LASTSTRINGINDEX'):config.
                                get_value('APPLICATIONPC')])
        # type不变
        cp_data.extend(
            data_hex[config.get_value('APPLICATIONPC'
                                      ):config.get_value('APPLICATIONPC') + 4])
        # size+5*4
        old_application_size = ApUtils.printhex(
            ApUtils.little_endian(
                data_hex[config.get_value('APPLICATIONPC') +
                         4:config.get_value('APPLICATIONPC') + 8]))
        new_application_size = int(old_application_size, 16) + 5 * 4
        cp_data.extend(ApUtils.encodehex(new_application_size))
        # linenumber+unknown+namespace+name+flag不变
        cp_data.extend(data_hex[config.get_value('APPLICATIONPC') +
                                8:config.get_value('APPLICATIONPC') + 28])
        # Attribute count +1
        old_attr_count = ApUtils.printhex(
            ApUtils.little_endian(
                data_hex[config.get_value('APPLICATIONPC') +
                         28:config.get_value('APPLICATIONPC') + 32]))
        new_attr_count = int(old_attr_count, 16) + 1
        cp_data.extend(ApUtils.encodehex(new_attr_count))
        # class attribute
        cp_data.extend(data_hex[config.get_value('APPLICATIONPC') +
                                32:config.get_value('APPLICATIONPC') + 36])

        # 接下来只需要解析一个属性即可,为了初始化一些基本字段
        old_attr_namespace = data_hex[config.get_value('APPLICATIONPC') +
                                      36:config.get_value('APPLICATIONPC') +
                                      40]
        # 定位到name在Stringpool的index
        name_index = config.global_list['STRINGPOOL'].index("name")

        # 这里属性是有一定顺序的,在name前面有theme,label,icon
        count = 0
        for j in range(int(old_attr_count, 16)):
            attr_num = int(
                ApUtils.printhex(
                    ApUtils.little_endian(
                        data_hex[config.get_value('APPLICATIONPC') + 36 + 4 +
                                 4 * j * 5:config.get_value('APPLICATIONPC') +
                                 36 + 4 + 4 * j * 5 + 4])), 16)
            attr_name = config.global_list['STRINGPOOL'][attr_num]
            if attr_name == "theme" or attr_name == "label" or attr_name == "icon":
                count += 1
                # 拷贝这些前面的属性
                cp_data.extend(
                    data_hex[config.get_value('APPLICATIONPC') + 36 +
                             4 * j * 5:config.get_value('APPLICATIONPC') + 36 +
                             4 * j * 5 + 20])

        # 新增name属性
        # namespace
        cp_data.extend(old_attr_namespace)
        # name
        cp_data.extend(ApUtils.encodehex(name_index))
        # valuestr
        cp_data.extend(ApUtils.encodehex(new_stringchunk_count - 1))
        # type,这里是String固定type
        cp_data.extend(["08", "00", "00", "03"])
        # data
        cp_data.extend(ApUtils.encodehex(new_stringchunk_count - 1))

        # 拷贝剩下的属性
        attr_index_start = config.get_value(
            'APPLICATIONPC') + 36 + 5 * count * 4
        attr_index = config.get_value('APPLICATIONPC') + 36 + 5 * int(
            old_attr_count, 16) * 4
        cp_data.extend(data_hex[attr_index_start:attr_index])

        # 剩下的拷贝
        cp_data.extend(data_hex[attr_index:])
    else:
        print("[ERROR]There is something wrong with application resolve!!!")
        exit(-1)

    ApUtils.writedata(cp_data, target_filepath)
    # 结束
    print("[ApEditor]Change Application success!!!")
Exemple #9
0
def resolver(am_path):
    print("[ApEditor]Begin to resolve AndroidManifest.xml")
    # 全局变量初始化
    config.init_global()

    # 读取二进制文件并转化成16进制
    data_hex = ApUtils.am_read(am_path)

    # 开始解析头部
    ApResolver.am_header(data_hex)
    # 解析后当前指针
    pc = config.get_value('AMHEADER')

    # 解析StringChunk
    ApResolver.am_stringchunk(data_hex, pc)
    pc = config.get_value('STRINGCHUNKEND')

    # 调整指针,预留16位
    config.set_value('RESOURCEIDCHUNKSTAR', pc)
    for ind in range(16):
        if ApUtils.printhex(
                ApUtils.little_endian(data_hex[pc + ind:pc + ind +
                                               4])) == "0x00080180":
            config.set_value('RESOURCEIDCHUNKSTAR',
                             config.get_value('RESOURCEIDCHUNKSTAR') + ind)
            break
    pc = config.get_value('RESOURCEIDCHUNKSTAR')

    # 解析resource chunk
    ApResolver.am_resourceidchunk(data_hex, pc)
    pc = config.get_value('RESOURCEIDCHUNKEND')
    # print pc

    # 开始进入循环解析
    while pc < len(data_hex):
        # namespace start
        if ApUtils.printhex(ApUtils.little_endian(
                data_hex[pc:pc + 4])) == "0x00100100":
            config.set_value('STARNAMESPACESTAR', pc)
            ApResolver.am_namespacechunk_star(data_hex, pc)
            pc = config.get_value('STARNAMESPACEEND')
        # tag start
        elif ApUtils.printhex(ApUtils.little_endian(
                data_hex[pc:pc + 4])) == "0x00100102":
            config.set_value('STARTTAGCHUNKSTAR', pc)
            ApResolver.am_tagchunk_star(data_hex, pc)
            pc = config.get_value('STARTTAGCHUNKEND')
            config.set_value('TAGCOUNTSTAR',
                             config.get_value('TAGCOUNTSTAR') + 1)
        # tag end
        elif ApUtils.printhex(ApUtils.little_endian(
                data_hex[pc:pc + 4])) == "0x00100103":
            config.set_value('ENDTAGCHUNKSTAR', pc)
            ApResolver.am_tagchunk_end(data_hex, pc)
            pc = config.get_value('ENDTAGCHUNKEND')
            config.set_value('TAGCOUNTEND',
                             config.get_value('TAGCOUNTEND') + 1)
        # tag end
        elif ApUtils.printhex(ApUtils.little_endian(
                data_hex[pc:pc + 4])) == "0x00100101":
            config.set_value('ENDNAMESPACESTAR', pc)
            ApResolver.am_namespacechunk_end(data_hex, pc)
            pc = config.get_value('ENDNAMESPACEEND')
        # text end
        elif ApUtils.printhex(ApUtils.little_endian(
                data_hex[pc:pc + 4])) == "0x00100104":
            config.set_value('TEXTCHUNKSTAR', pc)
            ApResolver.am_textchunk(data_hex, pc)
            pc = config.get_value('TEXTCHUNKEND')
        else:
            ApUtils.apprint("[error]NO type of the chunk,the pc is " + str(pc))
            exit(-1)

    # 解析结束
    print("[ApEditor]Resolve AndroidManifest.xml success!!!")
    return data_hex