Skip to content

Commit c730626

Browse files
committed
[5.7][Runtime] Don't try to demangle unprefixed untrusted names. Remove operator new/delete hackery.
The operator new/delete overrides aren't working out due to inconsistent inlining of std::string creation/deletion. We can end up creating one with the global new but destroying it with our local delete. If they aren't compatible, this crashes. Instead, avoid problematic new/delete activity coming from lookup of ObjC class names. Names passed to getObjCClassByMangledName/swift_stdlib_getTypeByMangledNameUntrusted must either have a standard mangled name prefix, start with a digit (for unprefixed mangled names) or use the convenience dot syntax. Check for those up front and immediately reject anything else. This has the added bonus of failing more quickly for non-Swift names. rdar://93863030 (cherry picked from commit 604eb05)
1 parent fec9add commit c730626

File tree

2 files changed

+31
-33
lines changed

2 files changed

+31
-33
lines changed

stdlib/public/runtime/Heap.cpp

Lines changed: 0 additions & 27 deletions
Original file line numberDiff line numberDiff line change
@@ -134,30 +134,3 @@ static void swift_slowDeallocImpl(void *ptr, size_t alignMask) {
134134
void swift::swift_slowDealloc(void *ptr, size_t bytes, size_t alignMask) {
135135
swift_slowDeallocImpl(ptr, alignMask);
136136
}
137-
138-
#if defined(__APPLE__) && defined(__MACH__) && SWIFT_STDLIB_HAS_DARWIN_LIBMALLOC
139-
// On Darwin, define our own, hidden operator new/delete implementations. We
140-
// don't want to pick up any overrides that come from other code, but we also
141-
// don't want to expose our overrides to any other code. We can't do this
142-
// directly in C++, as the compiler has an implicit prototype with default
143-
// visibility. However, if we implement them as C functions using the C++
144-
// mangled names, the compiler accepts them without complaint, and the linker
145-
// still links all internal uses with these overrides.
146-
147-
__attribute__((visibility(("hidden")))) extern "C" void *_Znwm(size_t size) {
148-
return swift_slowAlloc(size, MALLOC_ALIGN_MASK);
149-
}
150-
151-
__attribute__((visibility(("hidden")))) extern "C" void _ZdlPv(void *ptr) {
152-
swift_slowDeallocImpl(ptr, MALLOC_ALIGN_MASK);
153-
}
154-
155-
__attribute__((visibility(("hidden")))) extern "C" void *_Znam(size_t size) {
156-
return swift_slowAlloc(size, MALLOC_ALIGN_MASK);
157-
}
158-
159-
__attribute__((visibility(("hidden")))) extern "C" void _ZdaPv(void *ptr) {
160-
swift_slowDeallocImpl(ptr, MALLOC_ALIGN_MASK);
161-
}
162-
163-
#endif

stdlib/public/runtime/MetadataLookup.cpp

Lines changed: 31 additions & 6 deletions
Original file line numberDiff line numberDiff line change
@@ -1909,17 +1909,42 @@ swift_getTypeByMangledNameInContextInMetadataState(
19091909
}).getType().getMetadata();
19101910
}
19111911

1912-
/// Demangle a mangled name, but don't allow symbolic references.
1912+
static bool validateUntrustedName(llvm::StringRef typeName) {
1913+
size_t dotCount = false;
1914+
for (char c : typeName) {
1915+
// No symbolic references allowed in untrusted names.
1916+
if (c >= '\x01' && c <= '\x1F')
1917+
return false;
1918+
if (c == '.')
1919+
dotCount += 1;
1920+
}
1921+
1922+
// Accept any name with one dot.
1923+
if (dotCount == 1)
1924+
return true;
1925+
1926+
// Accept names with a mangling prefix.
1927+
if (getManglingPrefixLength(typeName))
1928+
return true;
1929+
1930+
// Accept names that start with a digit (unprefixed mangled names).
1931+
if (typeName.size() > 0 && isdigit(typeName[0]))
1932+
return true;
1933+
1934+
// Reject anything else.
1935+
return false;
1936+
}
1937+
1938+
/// Demangle a mangled name, but don't allow symbolic references, and require a
1939+
/// known prefix or a dot.
19131940
SWIFT_CC(swift) SWIFT_RUNTIME_STDLIB_INTERNAL
19141941
const Metadata *_Nullable
19151942
swift_stdlib_getTypeByMangledNameUntrusted(const char *typeNameStart,
19161943
size_t typeNameLength) {
19171944
llvm::StringRef typeName(typeNameStart, typeNameLength);
1918-
for (char c : typeName) {
1919-
if (c >= '\x01' && c <= '\x1F')
1920-
return nullptr;
1921-
}
1922-
1945+
if (!validateUntrustedName(typeName))
1946+
return nullptr;
1947+
19231948
return swift_getTypeByMangledName(MetadataState::Complete, typeName, nullptr,
19241949
{}, {}).getType().getMetadata();
19251950
}

0 commit comments

Comments
 (0)