Repository: apple/swift
File: lib/ClangImporter/ClangDerivedConformances.cpp (C++)

Code before:

  ASSERT(result && clangDecl && "this should not be called with nullptrs");

  // Skip synthesizing conformances if the associated Clang node is from
  // a module that doesn't require cplusplus, to prevent us from accidentally
  // pulling in Cxx/CxxStdlib modules when a client is importing a C library.
  //
  // We will still attempt to synthesize to account for scenarios where the
  // module specification is missing altogether.
  if (auto *clangModule = importer::getClangOwningModule(
          result->getClangNode(), Impl.getClangASTContext());
      clangModule && !requiresCPlusPlus(clangModule))
    return;

  // Automatic conformances: these may be applied to any type that fits the
  // requirements.
  conformToCxxIteratorIfNeeded(Impl, result, clangDecl);
  conformToCxxSequenceIfNeeded(Impl, result, clangDecl);
  conformToCxxConvertibleToBoolIfNeeded(Impl, result, clangDecl);

  // CxxStdlib conformances: these should only apply to known C++ stdlib types,
  // which we determine by name and membership in the std namespace.
  if (!clangDecl->getIdentifier() || !clangDecl->isInStdNamespace())
    return;
  auto ty = identifyCxxStdTypeByName(clangDecl->getName());
  if (!NonCopyableCxxStdTypeConformances.contains(ty) &&
      result->getAttrs().hasAttribute<MoveOnlyAttr>())
    return;

  switch (ty) {
  case CxxStdType::uncategorized:
    return;
  case CxxStdType::optional:
    conformToCxxOptional(Impl, result, clangDecl);
    return;
  case CxxStdType::set:
  case CxxStdType::unordered_set:
    conformToCxxSet(Impl, result, clangDecl, /*isUniqueSet=*/true);
    return;
  case CxxStdType::multiset:
    conformToCxxSet(Impl, result, clangDecl, /*isUniqueSet=*/false);
    return;
  case CxxStdType::pair:
    conformToCxxPair(Impl, result, clangDecl);
    return;
  case CxxStdType::map:
  case CxxStdType::unordered_map:
  case CxxStdType::multimap:
    conformToCxxDictionary(Impl, result, clangDecl);
    return;
  case CxxStdType::vector:

Review comment (suggestion):
I am wondering if we want something more general in the future, asking the compiler if the type satisfies the requirements of the protocol including copyability. 

Code after:
  // a module that doesn't require cplusplus, to prevent us from accidentally
  // pulling in Cxx/CxxStdlib modules when a client is importing a C library.
  //
  // We will still attempt to synthesize to account for scenarios where the
  // module specification is missing altogether.
  if (auto *clangModule = importer::getClangOwningModule(
          result->getClangNode(), Impl.getClangASTContext());
      clangModule && !requiresCPlusPlus(clangModule))
    return;

  // Automatic conformances: these may be applied to any type that fits the
  // requirements.
  conformToCxxIteratorIfNeeded(Impl, result, clangDecl);
  conformToCxxSequenceIfNeeded(Impl, result, clangDecl);
  conformToCxxConvertibleToBoolIfNeeded(Impl, result, clangDecl);

  // CxxStdlib conformances: these should only apply to known C++ stdlib types,
  // which we determine by name and membership in the std namespace.
  if (!clangDecl->getIdentifier() || !clangDecl->isInStdNamespace())
    return;

  auto ty = identifyCxxStdTypeByName(clangDecl->getName());
  switch (ty) {
  case CxxStdType::uncategorized:
    return;
  case CxxStdType::optional:
    conformToCxxOptional(Impl, result, clangDecl);
    return;
  case CxxStdType::set:
  case CxxStdType::unordered_set:
    conformToCxxSet(Impl, result, clangDecl, /*isUniqueSet=*/true);
    return;
  case CxxStdType::multiset:
    conformToCxxSet(Impl, result, clangDecl, /*isUniqueSet=*/false);
    return;
  case CxxStdType::pair:
    conformToCxxPair(Impl, result, clangDecl);
    return;
  case CxxStdType::map:
  case CxxStdType::unordered_map:
  case CxxStdType::multimap:
    conformToCxxDictionary(Impl, result, clangDecl);
    return;
  case CxxStdType::vector:
    conformToCxxVector(Impl, result, clangDecl);
    return;
  case CxxStdType::span:
    conformToCxxSpan(Impl, result, clangDecl);
    return;
  }
}