Skip to content

Commit abfd790

Browse files
authored
Merge pull request #62575 from apple/egorzhdan/cxx-disambiguate
[cxx-interop] Disambiguate const and non-const methods consistently
2 parents d7cf7fb + 168ef49 commit abfd790

File tree

7 files changed

+46
-69
lines changed

7 files changed

+46
-69
lines changed

lib/ClangImporter/ImportDecl.cpp

Lines changed: 0 additions & 57 deletions
Original file line numberDiff line numberDiff line change
@@ -2105,30 +2105,6 @@ namespace {
21052105
// The name of every member.
21062106
llvm::DenseSet<StringRef> allMemberNames;
21072107

2108-
// Cxx methods may have the same name but differ in "constness".
2109-
// In such a case we must differentiate in swift (See VisitFunction).
2110-
// Before importing the different CXXMethodDecl's we track functions
2111-
// that differ this way so we can disambiguate later
2112-
for (auto m : decl->decls()) {
2113-
if (auto method = dyn_cast<clang::CXXMethodDecl>(m)) {
2114-
if (method->getDeclName().isIdentifier()) {
2115-
auto contextMap = Impl.cxxMethods.find(method->getDeclContext());
2116-
if (contextMap == Impl.cxxMethods.end() ||
2117-
contextMap->second.find(method->getName()) ==
2118-
contextMap->second.end()) {
2119-
Impl.cxxMethods[method->getDeclContext()][method->getName()] = {};
2120-
}
2121-
if (method->isConst()) {
2122-
// Add to const set
2123-
Impl.cxxMethods[method->getDeclContext()][method->getName()].first.insert(method);
2124-
} else {
2125-
// Add to mutable set
2126-
Impl.cxxMethods[method->getDeclContext()][method->getName()].second.insert(method);
2127-
}
2128-
}
2129-
}
2130-
}
2131-
21322108
// FIXME: Import anonymous union fields and support field access when
21332109
// it is nested in a struct.
21342110
for (auto m : decl->decls()) {
@@ -2214,10 +2190,6 @@ namespace {
22142190
}
22152191

22162192
if (auto MD = dyn_cast<FuncDecl>(member)) {
2217-
2218-
// When 2 CXXMethods diff by "constness" alone we differentiate them
2219-
// by changing the name of one. That changed method needs to be added
2220-
// to the lookup table since it cannot be found lazily.
22212193
if (auto cxxMethod = dyn_cast<clang::CXXMethodDecl>(m)) {
22222194
auto cxxOperatorKind = cxxMethod->getOverloadedOperator();
22232195

@@ -2272,16 +2244,6 @@ namespace {
22722244
// Make sure the synthesized decl can be found by lookupDirect.
22732245
result->addMemberToLookupTable(opFuncDecl);
22742246
}
2275-
2276-
if (cxxMethod->getDeclName().isIdentifier()) {
2277-
auto &mutableFuncPtrs =
2278-
Impl.cxxMethods[cxxMethod->getDeclContext()]
2279-
[cxxMethod->getName()]
2280-
.second;
2281-
if (mutableFuncPtrs.contains(cxxMethod)) {
2282-
result->addMemberToLookupTable(member);
2283-
}
2284-
}
22852247
}
22862248
methods.push_back(MD);
22872249
continue;
@@ -3031,25 +2993,6 @@ namespace {
30312993
return nullptr;
30322994
}
30332995

3034-
// Handle cases where 2 CXX methods differ strictly in "constness"
3035-
// In such a case append a suffix ("Mutating") to the mutable version
3036-
// of the method when importing to swift
3037-
if(decl->getDeclName().isIdentifier()) {
3038-
const auto &cxxMethodPair = Impl.cxxMethods[decl->getDeclContext()][decl->getName()];
3039-
const auto &constFuncPtrs = cxxMethodPair.first;
3040-
const auto &mutFuncPtrs = cxxMethodPair.second;
3041-
3042-
// Check to see if this function has both const & mut versions and
3043-
// that this decl refers to the mutable version.
3044-
if (!constFuncPtrs.empty() && mutFuncPtrs.contains(decl)) {
3045-
auto newName = decl->getName().str() + "Mutating";
3046-
auto newId = dc->getASTContext().getIdentifier(newName);
3047-
auto oldArgNames = importedName.getDeclName().getArgumentNames();
3048-
auto newDeclName = DeclName(Impl.SwiftContext, newId, oldArgNames);
3049-
importedName.setDeclName(newDeclName);
3050-
}
3051-
}
3052-
30532996
DeclName name = accessorInfo ? DeclName() : importedName.getDeclName();
30542997
auto selfIdx = importedName.getSelfIndex();
30552998

lib/ClangImporter/ImportName.cpp

Lines changed: 28 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -2200,6 +2200,34 @@ ImportedName NameImporter::importNameImpl(const clang::NamedDecl *D,
22002200
}
22012201
}
22022202

2203+
SmallString<16> newName;
2204+
// Check if we need to rename the C++ method to disambiguate it.
2205+
if (auto method = dyn_cast<clang::CXXMethodDecl>(D)) {
2206+
if (!method->isConst() && !method->isOverloadedOperator()) {
2207+
// See if any other methods within the same struct have the same name, but
2208+
// differ in constness.
2209+
auto otherDecls = dc->lookup(method->getDeclName());
2210+
bool shouldRename = false;
2211+
for (auto otherDecl : otherDecls) {
2212+
if (otherDecl == D)
2213+
continue;
2214+
if (auto otherMethod = dyn_cast<clang::CXXMethodDecl>(otherDecl)) {
2215+
// TODO: what if the other method is also non-const?
2216+
if (otherMethod->isConst()) {
2217+
shouldRename = true;
2218+
break;
2219+
}
2220+
}
2221+
}
2222+
2223+
if (shouldRename) {
2224+
newName = baseName;
2225+
newName += "Mutating";
2226+
baseName = newName;
2227+
}
2228+
}
2229+
}
2230+
22032231
// swift_newtype-ed declarations may have common words with the type name
22042232
// stripped.
22052233
if (auto newtypeDecl = findSwiftNewtype(D, clangSema, version)) {

lib/ClangImporter/ImporterImpl.h

Lines changed: 0 additions & 8 deletions
Original file line numberDiff line numberDiff line change
@@ -614,14 +614,6 @@ class LLVM_LIBRARY_VISIBILITY ClangImporter::Implementation
614614
llvm::MapVector<std::pair<NominalTypeDecl *, Type>,
615615
std::pair<FuncDecl *, FuncDecl *>> cxxSubscripts;
616616

617-
/// Keep track of cxx function names, params etc in order to
618-
/// allow for de-duping functions that differ strictly on "constness".
619-
llvm::DenseMap<const clang::DeclContext *, llvm::DenseMap<llvm::StringRef,
620-
std::pair<
621-
llvm::DenseSet<clang::FunctionDecl *>,
622-
llvm::DenseSet<clang::FunctionDecl *>>>>
623-
cxxMethods;
624-
625617
// Keep track of the decls that were already cloned for this specific class.
626618
llvm::DenseMap<std::pair<ValueDecl *, DeclContext *>, ValueDecl *>
627619
clonedBaseMembers;
Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -1 +1 @@
1-
10
1+
11

test/Interop/Cxx/class/method/Inputs/ambiguous_methods.h

Lines changed: 9 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -47,4 +47,13 @@ struct HasAmbiguousMethods2 {
4747
}
4848
};
4949

50+
struct Unsafe {
51+
int *ptr;
52+
};
53+
54+
struct HasAmbiguousUnsafeMethods {
55+
Unsafe getUnsafe() const { return Unsafe(); }
56+
Unsafe getUnsafe() { return Unsafe(); }
57+
};
58+
5059
#endif // TEST_INTEROP_CXX_CLASS_AMBIGUOUS_METHOD_METHODS_H

test/Interop/Cxx/class/method/ambiguous-methods-module-interface.swift

Lines changed: 6 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -14,4 +14,9 @@
1414

1515
// CHECK: struct HasAmbiguousMethods2
1616
// CHECK: func increment(_ a: Int32) -> Int32
17-
// CHECK-NOT: mutating func incrementMutating(_ a: Int32) -> Int32
17+
// CHECK-NOT: mutating func incrementMutating(_ a: Int32) -> Int32
18+
19+
// CHECK: struct HasAmbiguousUnsafeMethods {
20+
// CHECK: func __getUnsafeUnsafe() -> Unsafe
21+
// CHECK: mutating func __getUnsafeMutatingUnsafe() -> Unsafe
22+
// CHECK: }

test/Interop/Cxx/stdlib/msvcprt-module-interface.swift

Lines changed: 2 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -12,10 +12,10 @@
1212
// CHECK-STRING: typealias size_t = size_t
1313
// CHECK-STRING: static func to_string(_ _Val: Int32) -> std.string
1414
// CHECK-STRING: static func to_wstring(_ _Val: Int32) -> std.wstring
15-
// CHECK-STRING: struct __CxxTemplateInstSs {
15+
// CHECK-STRING: struct __CxxTemplateInstSs : CxxRandomAccessCollection {
1616
// CHECK-STRING: typealias value_type = CChar
1717
// CHECK-STRING: }
18-
// CHECK-STRING: struct __CxxTemplateInstSbIwSt11char_traitsIwESaIwEE {
18+
// CHECK-STRING: struct __CxxTemplateInstSbIwSt11char_traitsIwESaIwEE : CxxRandomAccessCollection {
1919
// CHECK-STRING: typealias value_type = CWideChar
2020
// CHECK-STRING: }
2121
// CHECK-STRING: typealias string = std.__CxxTemplateInstSs

0 commit comments

Comments
 (0)