Merge pull request #9021 from naveenkaje/fix_part_size_check

tools: check that part size is not exceeding region size
pull/9639/head
Anna Bridge 2019-02-07 10:16:12 +00:00 committed by GitHub
commit 645c1cebb5
No known key found for this signature in database
GPG Key ID: 4AEE18F83AFDEB23
2 changed files with 46 additions and 5 deletions

View File

@ -411,7 +411,7 @@ def _fill_header(region_list, current_region):
return header
def merge_region_list(region_list, destination, notify, padding=b'\xFF'):
def merge_region_list(region_list, destination, notify, config, padding=b'\xFF'):
"""Merge the region_list into a single image
Positional Arguments:
@ -435,6 +435,13 @@ def merge_region_list(region_list, destination, notify, padding=b'\xFF'):
notify.info(" Filling region %s with %s" % (region.name, region.filename))
part = intelhex_offset(region.filename, offset=region.start)
part.start_addr = None
# Normally, we assume that part.maxddr() can be beyond
# end of rom. However, if the size is restricted with config, do check.
if config.target.restrict_size is not None:
part_size = (part.maxaddr() - part.minaddr()) + 1
if part_size > region.size:
raise ToolException("Contents of region %s does not fit"
% region.name)
merged.merge(part)
# Hex file can have gaps, so no padding needed. While other formats may
@ -555,13 +562,13 @@ def build_project(src_paths, build_path, target, toolchain_name,
for r in region_list]
res = "%s.%s" % (join(build_path, name),
getattr(toolchain.target, "OUTPUT_EXT", "bin"))
merge_region_list(region_list, res, notify)
merge_region_list(region_list, res, notify, toolchain.config)
update_regions = [
r for r in region_list if r.name in UPDATE_WHITELIST
]
if update_regions:
update_res = join(build_path, generate_update_filename(name, toolchain.target))
merge_region_list(update_regions, update_res, notify)
merge_region_list(update_regions, update_res, notify, toolchain.config)
res = (res, update_res)
else:
res = (res, None)

View File

@ -18,11 +18,14 @@ limitations under the License.
import unittest
from collections import namedtuple
from mock import patch, MagicMock
from tools.build_api import prepare_toolchain, build_project, build_library
from tools.build_api import prepare_toolchain, build_project, build_library, merge_region_list
from tools.resources import Resources
from tools.toolchains import TOOLCHAINS
from tools.notifier.mock import MockNotifier
from tools.config import Region
from tools.utils import ToolException
from intelhex import IntelHex
import intelhex
"""
Tests for build_api.py
"""
@ -240,5 +243,36 @@ class BuildApiTests(unittest.TestCase):
self.assertEqual(args[1]['app_config'], None,
"prepare_toolchain was called with an incorrect app_config")
@patch('tools.build_api.intelhex_offset')
@patch('tools.config')
def test_merge_region_no_fit(self, mock_config, mock_intelhex_offset):
"""
Test that merge region fails as expected when part size overflows region size.
"""
max_addr = 87444
# create a dummy hex file with above max_addr
mock_intelhex_offset.return_value = IntelHex({0:2, max_addr:0})
# create application and post-application regions and merge.
region_application = Region("application", 10000, 86000, True, "random.hex")
region_post_application = Region("postapplication", 100000, 90000, False, None)
notify = MockNotifier()
region_list = [region_application, region_post_application]
# path to store the result in, should not get used as we expect exception.
res = "./"
mock_config.target.restrict_size = 90000
toolexception = False
try:
merge_region_list(region_list, res, notify, mock_config)
except ToolException:
toolexception = True
except Exception as e:
print("%s %s" % (e.message, e.args))
self.assertTrue(toolexception, "Expected ToolException not raised")
if __name__ == '__main__':
unittest.main()