Skip to content

Commit d072cb8

Browse files
committed
Replace small with std C lib if not supported by a target's toolchain
Display a post-build warning indicating to the user that the standard C library was used instead of the small C library if the former is not supported.
1 parent 03dab7f commit d072cb8

File tree

6 files changed

+122
-16
lines changed

6 files changed

+122
-16
lines changed

tools/build_api.py

Lines changed: 10 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -48,6 +48,7 @@
4848
from .libraries import Library
4949
from .toolchains import TOOLCHAIN_CLASSES, TOOLCHAIN_PATHS
5050
from .toolchains.arm import UARM_TOOLCHAIN_WARNING
51+
from .toolchains.mbed_toolchain import is_std_c_lib_supported_instead_small_c_lib
5152
from .config import Config
5253

5354
RELEASE_VERSIONS = ['2', '5']
@@ -250,6 +251,15 @@ def find_valid_toolchain(target, toolchain):
250251
and "uARM" in {toolchain_name, target.default_toolchain}
251252
):
252253
end_warnings.append(UARM_TOOLCHAIN_WARNING)
254+
255+
if is_std_c_lib_supported_instead_small_c_lib(target, toolchain):
256+
warning = (
257+
"Warning: We noticed that you are using target.c_lib set to small.\n"
258+
"As the {} target does not support a small C library for the {} toolchain,\n"
259+
"we are using the standard C library instead. "
260+
).format(target.name, toolchain)
261+
end_warnings.append(warning)
262+
253263
return toolchain_name, internal_tc_name, end_warnings
254264
else:
255265
if last_error:

tools/test/toolchains/test_toolchains.py

Lines changed: 59 additions & 10 deletions
Original file line numberDiff line numberDiff line change
@@ -83,12 +83,12 @@ def test_arm_c_lib_std_exception(self):
8383

8484

8585
def test_arm_c_lib_small_exception(self):
86-
"""Test that an exception is raised if the small C library is not supported for a target on the ARM toolchain."""
86+
"""Test that an exception is raised if the small and std C library are not supported for a target on the ARM toolchain."""
8787
mock_target = mock.MagicMock()
8888
mock_target.core = "Cortex-M4"
8989
mock_target.c_lib = "small"
9090
del mock_target.default_lib
91-
mock_target.supported_c_libs = {"arm": ["std"]}
91+
mock_target.supported_c_libs = {"arm": [""]}
9292
mock_target.default_toolchain = "ARM"
9393
mock_target.supported_toolchains = ["ARM", "uARM", "ARMC5"]
9494
with self.assertRaisesRegexp(NotSupportedException, UNSUPPORTED_C_LIB_EXCEPTION_STRING.format(mock_target.c_lib)):
@@ -97,6 +97,27 @@ def test_arm_c_lib_small_exception(self):
9797
with self.assertRaisesRegexp(NotSupportedException, UNSUPPORTED_C_LIB_EXCEPTION_STRING.format(mock_target.c_lib)):
9898
ARMC6(mock_target)
9999

100+
def test_arm_small_c_lib_swap_std_lib(self):
101+
"""Test that no exception is raised when small c lib is not supported but std lib is supported."""
102+
mock_target = mock.MagicMock()
103+
mock_target.core = "Cortex-M4"
104+
mock_target.c_lib = "small"
105+
del mock_target.default_lib
106+
mock_target.supported_c_libs = {"arm": ["std"]}
107+
mock_target.supported_toolchains = ["ARM", "uARM", "ARMC5"]
108+
109+
mock_target.default_toolchain = "ARM"
110+
try:
111+
ARM_STD(mock_target)
112+
except NotSupportedException:
113+
self.fail(UNSUPPORTED_C_LIB_EXCEPTION_STRING.format(mock_target.c_lib))
114+
115+
mock_target.default_toolchain = "ARMC6"
116+
try:
117+
ARMC6(mock_target)
118+
except NotSupportedException:
119+
self.fail(UNSUPPORTED_C_LIB_EXCEPTION_STRING.format(mock_target.c_lib))
120+
100121
class TestGccToolchain(TestCase):
101122
"""Test the GCC class."""
102123

@@ -147,25 +168,39 @@ def test_gcc_arm_c_lib_std_exception(self):
147168
"""Test that an exception is raised if the std C library is not supported for a target on the GCC_ARM toolchain."""
148169
mock_target = mock.MagicMock()
149170
mock_target.core = "Cortex-M4"
150-
mock_target.default_toolchain = "ARM"
171+
mock_target.default_toolchain = "GCC_ARM"
151172
mock_target.c_lib = "std"
152173
del mock_target.default_lib
153-
mock_target.supported_c_libs = {"arm": ["small"]}
174+
mock_target.supported_c_libs = {"gcc_arm": ["small"]}
154175
with self.assertRaisesRegexp(NotSupportedException, UNSUPPORTED_C_LIB_EXCEPTION_STRING.format(mock_target.c_lib)):
155176
GCC_ARM(mock_target)
156177

157178
def test_gcc_arm_c_lib_small_exception(self):
158-
"""Test that an exception is raised if the small C library is not supported for a target on the GCC_ARM toolchain."""
179+
"""Test that an exception is raised if the small and std C library are not supported for a target on the GCC_ARM toolchain."""
159180
mock_target = mock.MagicMock()
160181
mock_target.core = "Cortex-M4"
161182
mock_target.c_lib = "small"
162183
del mock_target.default_lib
163-
mock_target.supported_c_libs = {"arm": ["std"]}
164-
mock_target.default_toolchain = "ARM"
165-
mock_target.supported_toolchains = ["ARM", "uARM", "ARMC5"]
184+
mock_target.supported_c_libs = {"gcc_arm": [""]}
185+
mock_target.default_toolchain = "GCC_ARM"
186+
mock_target.supported_toolchains = ["GCC_ARM"]
166187
with self.assertRaisesRegexp(NotSupportedException, UNSUPPORTED_C_LIB_EXCEPTION_STRING.format(mock_target.c_lib)):
167188
GCC_ARM(mock_target)
168189

190+
def test_gcc_arm_small_c_lib_swap_std_lib(self):
191+
"""Test that no exception is raised when small c lib is not supported but std lib is supported."""
192+
mock_target = mock.MagicMock()
193+
mock_target.core = "Cortex-M4"
194+
mock_target.supported_c_libs = {"gcc_arm": ["std"]}
195+
mock_target.c_lib = "small"
196+
del mock_target.default_lib
197+
mock_target.supported_toolchains = ["GCC_ARM"]
198+
mock_target.is_TrustZone_secure_target = False
199+
mock_target.default_toolchain = "GCC_ARM"
200+
try:
201+
GCC_ARM(mock_target)
202+
except NotSupportedException:
203+
self.fail(UNSUPPORTED_C_LIB_EXCEPTION_STRING.format(mock_target.c_lib))
169204
class TestIarToolchain(TestCase):
170205
"""Test the IAR class."""
171206

@@ -210,12 +245,26 @@ def test_iar_c_lib_std_exception(self):
210245
IAR(mock_target)
211246

212247
def test_iar_c_lib_small_exception(self):
213-
"""Test that an exception is raised if the small C library is not supported for a target on the IAR toolchain."""
248+
"""Test that an exception is raised if the small and std C library are not supported for a target on the IAR toolchain."""
214249
mock_target = mock.MagicMock()
215250
mock_target.core = "Cortex-M4"
216251
mock_target.c_lib = "small"
217252
del mock_target.default_lib
218-
mock_target.supported_c_libs = {"iar": ["std"]}
253+
mock_target.supported_c_libs = {"iar": [""]}
219254
mock_target.supported_toolchains = ["IAR"]
220255
with self.assertRaisesRegexp(NotSupportedException, UNSUPPORTED_C_LIB_EXCEPTION_STRING.format(mock_target.c_lib)):
221256
IAR(mock_target)
257+
258+
def test_iar_small_c_lib_swap_std_lib(self):
259+
"""Test that no exception is raised when small c lib is not supported but std lib is supported."""
260+
mock_target = mock.MagicMock()
261+
mock_target.core = "Cortex-M4"
262+
mock_target.supported_c_libs = {"iar": ["std"]}
263+
mock_target.c_lib = "small"
264+
del mock_target.default_lib
265+
mock_target.supported_toolchains = ["IAR"]
266+
mock_target.is_TrustZone_secure_target = False
267+
try:
268+
IAR(mock_target)
269+
except NotSupportedException:
270+
self.fail(UNSUPPORTED_C_LIB_EXCEPTION_STRING.format(mock_target.c_lib))

tools/toolchains/arm.py

Lines changed: 17 additions & 3 deletions
Original file line numberDiff line numberDiff line change
@@ -26,7 +26,9 @@
2626
from shutil import rmtree
2727
from distutils.version import LooseVersion
2828

29-
from tools.toolchains.mbed_toolchain import mbedToolchain, TOOLCHAIN_PATHS
29+
from tools.toolchains.mbed_toolchain import (
30+
mbedToolchain, TOOLCHAIN_PATHS, is_std_c_lib_supported_instead_small_c_lib
31+
)
3032
from tools.utils import mkdir, NotSupportedException, run_cmd
3133
from tools.resources import FileRef
3234

@@ -70,7 +72,13 @@ def __init__(self, target, notify=None, macros=None,
7072
raise NotSupportedException(
7173
"this compiler does not support the core %s" % target.core)
7274

73-
self.check_c_lib_supported(target, "arm")
75+
toolchain = "arm"
76+
77+
if is_std_c_lib_supported_instead_small_c_lib(target, toolchain):
78+
# Replace small C lib with std if there is no small C lib support
79+
target.c_lib = "std"
80+
81+
self.check_c_lib_supported(target, toolchain)
7482

7583
if (
7684
getattr(target, "default_toolchain", "ARM") == "uARM"
@@ -562,7 +570,13 @@ def __init__(self, target, *args, **kwargs):
562570
"ARM/ARMC6 compiler support is required for ARMC6 build"
563571
)
564572

565-
self.check_c_lib_supported(target, "arm")
573+
toolchain = "arm"
574+
575+
if is_std_c_lib_supported_instead_small_c_lib(target, toolchain):
576+
# Replace small C lib with std if there is no small C lib support
577+
target.c_lib = "std"
578+
579+
self.check_c_lib_supported(target, toolchain)
566580

567581
if (
568582
getattr(target, "default_toolchain", "ARMC6") == "uARM"

tools/toolchains/gcc.py

Lines changed: 10 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -22,7 +22,9 @@
2222
from distutils.spawn import find_executable
2323
from distutils.version import LooseVersion
2424

25-
from tools.toolchains.mbed_toolchain import mbedToolchain, TOOLCHAIN_PATHS
25+
from tools.toolchains.mbed_toolchain import (
26+
mbedToolchain, TOOLCHAIN_PATHS, is_std_c_lib_supported_instead_small_c_lib
27+
)
2628
from tools.utils import run_cmd
2729

2830

@@ -54,7 +56,13 @@ def __init__(self, target, notify=None, macros=None, build_profile=None,
5456
# Add flags for current size setting
5557
c_lib = "std"
5658
if hasattr(target, "c_lib"):
57-
self.check_c_lib_supported(target, "gcc_arm")
59+
toolchain = "gcc_arm"
60+
61+
if is_std_c_lib_supported_instead_small_c_lib(target, toolchain):
62+
# Replace small C lib with std if there is no small C lib support
63+
target.c_lib = "std"
64+
65+
self.check_c_lib_supported(target, toolchain)
5866
c_lib = target.c_lib
5967
elif hasattr(target, "default_build"):
6068
c_lib = target.default_build

tools/toolchains/iar.py

Lines changed: 9 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -20,7 +20,9 @@
2020
from os.path import join, splitext, exists
2121
from distutils.version import LooseVersion
2222

23-
from tools.toolchains.mbed_toolchain import mbedToolchain, TOOLCHAIN_PATHS
23+
from tools.toolchains.mbed_toolchain import (
24+
mbedToolchain, TOOLCHAIN_PATHS, is_std_c_lib_supported_instead_small_c_lib
25+
)
2426
from tools.utils import run_cmd
2527

2628
class IAR(mbedToolchain):
@@ -54,6 +56,12 @@ def __init__(self, target, notify=None, macros=None, build_profile=None,
5456
build_profile=build_profile
5557
)
5658

59+
toolchain = "iar"
60+
61+
if is_std_c_lib_supported_instead_small_c_lib(target, toolchain):
62+
# Replace small C lib with std if there is no small C lib support
63+
target.c_lib = "std"
64+
5765
self.check_c_lib_supported(target, "iar")
5866

5967
if target.is_TrustZone_secure_target:

tools/toolchains/mbed_toolchain.py

Lines changed: 17 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -1393,3 +1393,20 @@ def report(self):
13931393
to_ret['linker'] = {'flags': copy(self.flags['ld'])}
13941394
to_ret.update(self.config.report)
13951395
return to_ret
1396+
1397+
def is_std_c_lib_supported_instead_small_c_lib(target, toolchain):
1398+
"""
1399+
Check if the standard C lib should be used instead of the small C lib.
1400+
Return True if the target does not support a small C lib for a given
1401+
toolchain but supports the standard C library instead.
1402+
"""
1403+
if (
1404+
hasattr(target, "c_lib")
1405+
and target.c_lib.lower() == "small"
1406+
and hasattr(target, "supported_c_libs")
1407+
and toolchain.lower() in target.supported_c_libs
1408+
):
1409+
return (
1410+
"small" not in target.supported_c_libs[toolchain.lower()]
1411+
and "std" in target.supported_c_libs[toolchain.lower()]
1412+
)

0 commit comments

Comments
 (0)