[Feature][Modem]Update MTK MODEM V1.6 baseline version: MOLY.NR15.R3.MD700.IVT.MP1MR3.MP.V1.6
MTK modem version: MT2735_IVT_MOLY.NR15.R3.MD700.IVT.MP1MR3.MP.V1.6.tar.gz
RF modem version: NA
Change-Id: I45a4c2752fa9d1a618beacd5d40737fb39ab64fb
diff --git a/mcu/tools/mertos/mer_utility.py b/mcu/tools/mertos/mer_utility.py
new file mode 100644
index 0000000..3d08763
--- /dev/null
+++ b/mcu/tools/mertos/mer_utility.py
@@ -0,0 +1,218 @@
+#!/usr/bin/python
+# ****************************************************************************
+# Copyright Statement:
+# --------------------
+# This software is protected by Copyright and the information contained
+# herein is confidential. The software may not be copied and the information
+# contained herein may not be used or disclosed except with the written
+# permission of MediaTek Inc. (C) 2018
+#
+# BY OPENING THIS FILE, BUYER HEREBY UNEQUIVOCALLY ACKNOWLEDGES AND AGREES
+# THAT THE SOFTWARE/FIRMWARE AND ITS DOCUMENTATIONS ("MEDIATEK SOFTWARE")
+# RECEIVED FROM MEDIATEK AND/OR ITS REPRESENTATIVES ARE PROVIDED TO BUYER ON
+# AN "AS-IS" BASIS ONLY. MEDIATEK EXPRESSLY DISCLAIMS ANY AND ALL WARRANTIES,
+# EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE IMPLIED WARRANTIES OF
+# MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE OR NONINFRINGEMENT.
+# NEITHER DOES MEDIATEK PROVIDE ANY WARRANTY WHATSOEVER WITH RESPECT TO THE
+# SOFTWARE OF ANY THIRD PARTY WHICH MAY BE USED BY, INCORPORATED IN, OR
+# SUPPLIED WITH THE MEDIATEK SOFTWARE, AND BUYER AGREES TO LOOK ONLY TO SUCH
+# THIRD PARTY FOR ANY WARRANTY CLAIM RELATING THERETO. MEDIATEK SHALL ALSO
+# NOT BE RESPONSIBLE FOR ANY MEDIATEK SOFTWARE RELEASES MADE TO BUYER'S
+# SPECIFICATION OR TO CONFORM TO A PARTICULAR STANDARD OR OPEN FORUM.
+#
+# BUYER'S SOLE AND EXCLUSIVE REMEDY AND MEDIATEK'S ENTIRE AND CUMULATIVE
+# LIABILITY WITH RESPECT TO THE MEDIATEK SOFTWARE RELEASED HEREUNDER WILL BE,
+# AT MEDIATEK'S OPTION, TO REVISE OR REPLACE THE MEDIATEK SOFTWARE AT ISSUE,
+# OR REFUND ANY SOFTWARE LICENSE FEES OR SERVICE CHARGE PAID BY BUYER TO
+# MEDIATEK FOR SUCH MEDIATEK SOFTWARE AT ISSUE.
+#
+# THE TRANSACTION CONTEMPLATED HEREUNDER SHALL BE CONSTRUED IN ACCORDANCE
+# WITH THE LAWS OF THE STATE OF CALIFORNIA, USA, EXCLUDING ITS CONFLICT OF
+# LAWS PRINCIPLES. ANY DISPUTES, CONTROVERSIES OR CLAIMS ARISING THEREOF AND
+# RELATED THERETO SHALL BE SETTLED BY ARBITRATION IN SAN FRANCISCO, CA, UNDER
+# THE RULES OF THE INTERNATIONAL CHAMBER OF COMMERCE (ICC).
+#
+# ****************************************************************************
+#
+# ****************************************************************************
+#
+# Filename:
+# ---------
+# mer_utility.py
+#
+# Project:
+# --------
+# MERTOS
+#
+# Description:
+# ------------
+# Provide utilities used by MERTOS code generating.
+#
+#
+# Author:
+# -------
+# Ke-Ting Chen (mtk03141)
+#
+# ****************************************************************************
+
+import struct
+import subprocess
+
+
+class ElfDataExtractor(object):
+ def __init__(self, readelf_exec, elf_path):
+ self.elf_path = elf_path
+
+ # Get symbol table
+ # Example lines:
+ # Num: Value Size Type Bind Vis Ndx Name
+ # 20: 00000b1c 5216 OBJECT GLOBAL DEFAULT 9 sys_comp_config_tbl
+ self.symbols = {}
+ symbol_text_lines = subprocess.check_output([readelf_exec, '--symbols',
+ '--wide', elf_path]).splitlines()
+ for line in symbol_text_lines:
+ if line and line.lstrip()[0].isdigit():
+ contents = line.split()
+ if len(contents) == 7:
+ contents.append(contents[0][:-1])
+ #print contents[0][:-1]
+ self.symbols[contents[7]] = {
+ 'name': contents[7],
+ 'type': contents[3],
+ 'section_number': (int(contents[6]) if contents[6].isdigit() else contents[6]),
+ 'address': int(contents[1], 16),
+ 'size': int(contents[2]),
+ 'number': int(contents[0][:-1])}
+
+ # Assumes there is no hole in the number
+ self.symbol_list = sorted(self.symbols.viewvalues(), key=lambda x: x['number'])
+
+ # Get section info
+ # Example lines:
+ # [Nr] Name Type Addr Off Size ES Flg Lk Inf Al
+ # [ 9] .rodata PROGBITS 00000000 000aa0 00231c 00 A 0 0 4
+ self.sections = {}
+ section_text_lines = subprocess.check_output([readelf_exec, '--sections',
+ '--wide', elf_path]).splitlines()
+ for line in section_text_lines:
+ line = line.translate(None, '[]').lstrip()
+ if line and line[0].isdigit():
+ contents = line.split()
+ if contents[0] == '0':
+ self.sections['NULL'] = {'name': 'NULL', 'number': 0,
+ 'address': 0, 'offset': 0, 'size': 0}
+ else:
+ self.sections[contents[1]] = {
+ 'name': contents[1], 'number': int(contents[0]),
+ 'address': int(contents[3], 16), 'offset': int(contents[4], 16),
+ 'size': int(contents[5], 16)}
+
+ # Assumes there is no hole in the section number
+ self.section_list = sorted(self.sections.viewvalues(), key=lambda x: x['number'])
+
+ # Get relocation tables
+ self.relocations = {}
+ with open(elf_path, 'rb') as elf_file:
+ for name, section in self.sections.viewitems():
+ if name.startswith('.rel.') or name.startswith('.rela.'):
+ elf_file.seek(section['offset'])
+ raw_data = elf_file.read(section['size'])
+ if name.startswith('.rel.'):
+ #print 'processing ' + name
+ relocation = self.unpack_data_struct_array(
+ raw_data, '=IxHx', ['offset', 'symbol_number'])
+ for reloc_info in relocation:
+ reloc_info['addend'] = 0
+ name = name[len('.rel'):]
+ else:
+ relocation = self.unpack_data_struct_array(
+ raw_data, '=IBHxI', ['offset', 'type', 'symbol_number', 'addend'])
+ #print 'processing ' + name
+ name = name[len('.rela'):]
+ relocation.sort(key=lambda x: x['offset'])
+ self.relocations[name] = relocation
+
+ # Read in the elf and perform relocation to simplify query
+ elf_data = list(open(elf_path, 'rb').read())
+ for section_name, relocation in self.relocations.viewitems():
+ section_offset = self.sections[section_name]['offset']
+ for reloc_info in relocation:
+ elf_address = reloc_info['offset'] + section_offset
+ symbol = self.symbol_list[reloc_info['symbol_number']]
+ #print symbol['name'], reloc_info['symbol_number'], symbol['type']
+ if symbol['type'] == 'SECTION':
+ section = self.section_list[symbol['section_number']]
+ original_value = struct.unpack_from(
+ 'I', ''.join(elf_data[elf_address:elf_address + 4]))[0]
+ fill_data = original_value + section['offset'] + reloc_info['addend']
+ #print 'SECTION', symbol['name'], elf_data[elf_address:elf_address+4], hex(fill_data), hex(original_value)
+ else:
+ fill_data = reloc_info['symbol_number'] | 0x80000000
+ #print 'OTHER', symbol['name'], elf_data[elf_address:elf_address+4], hex(fill_data)
+ elf_data[elf_address:elf_address + 4] = struct.pack('I', fill_data)
+ elf_data = ''.join(elf_data)
+
+ # Get symbol data from elf
+ for symbol in self.symbols.viewvalues():
+ if symbol['size'] != 0:
+ # Get the content address in elf
+ section = self.section_list[symbol['section_number']]
+ address_offset = symbol['address'] - section['address']
+ elf_address = address_offset + section['offset']
+ # Get content from elf file
+ symbol['data'] = elf_data[elf_address:elf_address + symbol['size']]
+
+ def get_symbol_data(self, symbol_name):
+ return self.symbols[symbol_name]['data']
+
+ def get_symbol_section_name(self, symbol_name):
+ return self.section_list[
+ self.symbols[symbol_name]['section_number']]['name']
+
+ def get_symbol_name(self, target_address):
+ if target_address | 0x80000000:
+ symbol_number = target_address & 0x7FFFFFFF
+ return self.symbol_list[symbol_number]['name']
+ else:
+ for symbol in self.symbol_list:
+ if symbol['offset'] == target_address:
+ return symbol['name']
+ else:
+ return 'SYMBOL_NOT_FOUND'
+
+ def get_string_data(self, target_address):
+ elf_address = target_address
+
+ with open(self.elf_path, 'rb') as elf_file:
+ elf_file.seek(elf_address)
+ contents = ''
+ find_begin_index = 0
+ while 1:
+ contents += elf_file.read(32)
+ string_end_index = contents.find('\x00', find_begin_index)
+ if string_end_index == -1:
+ find_begin_index = len(contents)
+ else:
+ contents = contents[:string_end_index+1]
+ break
+ return contents
+
+ def unpack_symbol_data(self, format_string, symbol_name):
+ return struct.unpack_from(format_string, self.get_symbol_data(symbol_name))
+
+ def unpack_data_struct_array(self, raw_data, struct_format_string, field_names):
+ struct_size = struct.calcsize(struct_format_string)
+ array_length = len(raw_data) / struct_size
+ array = []
+ #print len(raw_data), struct_size, struct_format_string, field_names
+
+ for index in xrange(array_length):
+ data = struct.unpack_from(struct_format_string, raw_data, struct_size * index)
+ entry = dict(zip(field_names, data))
+ array.append(entry)
+
+ return array
+
+ def unpack_symbol_data_struct_array(self, symbol_name, struct_format_string, field_names):
+ raw_data = self.get_symbol_data(symbol_name)
+ return self.unpack_data_struct_array(raw_data, struct_format_string, field_names)