Skip to content

Commit 9f6879d

Browse files
committed
_FoundationUnicode: apply symbol renaming for non-Darwin targets
When building on non-Darwin targets, we are not guaranteed that there is no ICU library on the system (Windows ships an ICU since Windows 1703 (RedStone 2), SDK 10.0.15063. This now is implicitly pulled in OneCore.lib which vends the memory API contract; Linux normally ships a copy of ICU; android ships a copy of ICU since Android 6.0 (API Level 23) but is not part of the supported APIs). The availability of ICU on the system and in Swift causes a conflict. As there is no stable ABI for ICU, this is a problem and can cause spurious failures. Such a failure has been observed on Windows when statically linking Foundation. Unfortunately, the symbol renaming support in ICU relies on the `U_ICU_ENTRY_POINT_RENAME` macro which is defined thusly: ``` #define U_DEF_ICU_ENTRY_POINT_RENAME(x, y, z) x ## y ## z #define U_DEF2_ICU_ENTRY_POINT_RENAME(x, y, z) U_DEF_ICU_ENTRY_POINT_RENAME(x, y, z) #define U_ICU_ENTRY_POINT_RENAME(name) U_DEF2_ICU_ENTRY_POINT_RENAME(name, ICU_VERSION_SUFFIX, U_LIB_SUFFIX_C_NAME) ``` This macro is too complex for the clang importer to import into Swift, making this not possible to use directly. Instead, we manually perform the expansion of the CPP macros, using the `swift_` prefix instead to isolate and namespace our implementation. Unfortunately, even the aliasing macro is too complex for the clang importer to import directly. Because changing all the call sites would not be tractable (nor maintainable), this will require an additional change (swiftlang/swift#81840) to support aliasing macros to be imported into Swift. Although in theory only the dynamically linked version should be susceptible to the interpositioning issue, if any of the system libraries causes ICU to be included (e.g. a linker script on Unix or an import library pulling in another version), we can also hit this issue in the statically linked scenario. When dynamically linking, on Windows at least, it would not be a problem if the symbol is bound properly at link time as the symbolic resolution involves two-level namespacing, which is not available on ELF hosts. On Darwin, we cannot perform the renaming as the library is vended by the system and this would constitute an ABI break.
1 parent fa359a2 commit 9f6879d

File tree

3 files changed

+1970
-2
lines changed

3 files changed

+1970
-2
lines changed

CMakeLists.txt

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -45,7 +45,7 @@ add_compile_definitions(
4545
$<$<COMPILE_LANGUAGE:C,CXX>:U_HAVE_STRTOD_L=1>
4646
$<$<COMPILE_LANGUAGE:C,CXX>:U_HAVE_XLOCALE_H=1>
4747
$<$<COMPILE_LANGUAGE:C,CXX>:U_HAVE_STRING_VIEW=1>
48-
$<$<COMPILE_LANGUAGE:C,CXX>:U_DISABLE_RENAMING=1>
48+
$<$<COMPILE_LANGUAGE:C,CXX>:U_DISABLE_RENAMING=$<IF:$<PLATFORM_ID:Darwin>,1,0>>
4949
$<$<COMPILE_LANGUAGE:C,CXX>:U_COMBINED_IMPLEMENTATION>
5050
$<$<COMPILE_LANGUAGE:C,CXX>:U_COMMON_IMPLEMENTATION>
5151
$<$<COMPILE_LANGUAGE:C,CXX>:U_I18N_IMPLEMENTATION>

icuSources/include/_foundation_unicode/uconfig.h

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -101,7 +101,7 @@
101101
#ifndef U_DISABLE_RENAMING
102102
#if APPLE_ICU_CHANGES
103103
//rdar://60884991 #58 Replace installsrc patching with changes directly in header files
104-
#define U_DISABLE_RENAMING 1
104+
#define U_DISABLE_RENAMING defined(__APPLE__)
105105
#else
106106
#define U_DISABLE_RENAMING 0
107107
#endif // APPLE_ICU_CHANGES

0 commit comments

Comments
 (0)