mirror of
https://github.com/apple/swift.git
synced 2025-12-14 20:36:38 +01:00
Merge pull request #85123 from hnrklssn/swiftify-obj-c2
[ClangImporter] Attach _SwiftifyImportProtocol to imported protocols with bounds attributes
This commit is contained in:
@@ -5847,6 +5847,8 @@ namespace {
|
||||
|
||||
result->setMemberLoader(&Impl, 0);
|
||||
|
||||
Impl.swiftifyProtocol(result);
|
||||
|
||||
return result;
|
||||
}
|
||||
|
||||
|
||||
@@ -1828,6 +1828,7 @@ public:
|
||||
void addOptionSetTypealiases(NominalTypeDecl *nominal);
|
||||
|
||||
void swiftify(AbstractFunctionDecl *MappedDecl);
|
||||
void swiftifyProtocol(NominalTypeDecl *MappedDecl);
|
||||
|
||||
/// Find the lookup table that corresponds to the given Clang module.
|
||||
///
|
||||
|
||||
@@ -16,6 +16,7 @@
|
||||
|
||||
#include "ImporterImpl.h"
|
||||
#include "swift/AST/ASTContext.h"
|
||||
#include "swift/AST/ASTPrinter.h"
|
||||
#include "swift/AST/Decl.h"
|
||||
#include "swift/AST/DiagnosticsClangImporter.h"
|
||||
#include "swift/AST/ParameterList.h"
|
||||
@@ -36,29 +37,87 @@ namespace {
|
||||
ValueDecl *getKnownSingleDecl(ASTContext &SwiftContext, StringRef DeclName) {
|
||||
SmallVector<ValueDecl *, 1> decls;
|
||||
SwiftContext.lookupInSwiftModule(DeclName, decls);
|
||||
assert(decls.size() < 2);
|
||||
ASSERT(decls.size() < 2);
|
||||
if (decls.size() != 1) return nullptr;
|
||||
return decls[0];
|
||||
}
|
||||
|
||||
class SwiftifyInfoPrinter {
|
||||
public:
|
||||
struct SwiftifyInfoPrinter {
|
||||
static const ssize_t SELF_PARAM_INDEX = -2;
|
||||
static const ssize_t RETURN_VALUE_INDEX = -1;
|
||||
clang::ASTContext &ctx;
|
||||
ASTContext &SwiftContext;
|
||||
llvm::raw_ostream &out;
|
||||
llvm::raw_svector_ostream &out;
|
||||
MacroDecl &SwiftifyImportDecl;
|
||||
bool firstParam = true;
|
||||
llvm::StringMap<std::string> typeMapping;
|
||||
llvm::StringMap<std::string> &typeMapping;
|
||||
|
||||
protected:
|
||||
SwiftifyInfoPrinter(clang::ASTContext &ctx, ASTContext &SwiftContext,
|
||||
llvm::raw_ostream &out, MacroDecl &SwiftifyImportDecl)
|
||||
llvm::raw_svector_ostream &out,
|
||||
MacroDecl &SwiftifyImportDecl,
|
||||
llvm::StringMap<std::string> &typeMapping)
|
||||
: ctx(ctx), SwiftContext(SwiftContext), out(out),
|
||||
SwiftifyImportDecl(SwiftifyImportDecl) {
|
||||
out << "(";
|
||||
SwiftifyImportDecl(SwiftifyImportDecl), typeMapping(typeMapping) {}
|
||||
|
||||
public:
|
||||
void printTypeMapping() {
|
||||
printSeparator();
|
||||
out << "typeMappings: [";
|
||||
if (typeMapping.empty()) {
|
||||
out << ":]";
|
||||
return;
|
||||
}
|
||||
~SwiftifyInfoPrinter() { out << ")"; }
|
||||
llvm::interleaveComma(typeMapping, out, [&](const auto &entry) {
|
||||
out << '"' << entry.getKey() << "\" : \"" << entry.getValue() << '"';
|
||||
});
|
||||
out << "]";
|
||||
}
|
||||
|
||||
void printAvailability() {
|
||||
if (!hasMacroParameter("spanAvailability"))
|
||||
return;
|
||||
printSeparator();
|
||||
out << "spanAvailability: ";
|
||||
printAvailabilityOfType("Span");
|
||||
}
|
||||
private:
|
||||
bool hasMacroParameter(StringRef ParamName) {
|
||||
for (auto *Param : *SwiftifyImportDecl.parameterList)
|
||||
if (Param->getArgumentName().str() == ParamName)
|
||||
return true;
|
||||
return false;
|
||||
}
|
||||
|
||||
void printAvailabilityOfType(StringRef Name) {
|
||||
ValueDecl *D = getKnownSingleDecl(SwiftContext, Name);
|
||||
out << "\"";
|
||||
llvm::SaveAndRestore<bool> hasAvailbilitySeparatorRestore(firstParam, true);
|
||||
for (auto attr : D->getSemanticAvailableAttrs(/*includingInactive=*/true)) {
|
||||
auto introducedOpt = attr.getIntroduced();
|
||||
if (!introducedOpt.has_value()) continue;
|
||||
printSeparator();
|
||||
out << prettyPlatformString(attr.getPlatform()) << " " << introducedOpt.value();
|
||||
}
|
||||
out << "\"";
|
||||
}
|
||||
|
||||
protected:
|
||||
void printSeparator() {
|
||||
if (!firstParam) {
|
||||
out << ", ";
|
||||
} else {
|
||||
firstParam = false;
|
||||
}
|
||||
}
|
||||
};
|
||||
|
||||
struct SwiftifyInfoFunctionPrinter : public SwiftifyInfoPrinter {
|
||||
SwiftifyInfoFunctionPrinter(clang::ASTContext &ctx, ASTContext &SwiftContext,
|
||||
llvm::raw_svector_ostream &out,
|
||||
MacroDecl &SwiftifyImportDecl,
|
||||
llvm::StringMap<std::string> &typeMapping)
|
||||
: SwiftifyInfoPrinter(ctx, SwiftContext, out, SwiftifyImportDecl, typeMapping) {}
|
||||
|
||||
void printCountedBy(const clang::CountAttributedType *CAT,
|
||||
ssize_t pointerIndex) {
|
||||
@@ -109,56 +168,7 @@ public:
|
||||
return false;
|
||||
}
|
||||
|
||||
void printTypeMapping() {
|
||||
printSeparator();
|
||||
out << "typeMappings: [";
|
||||
if (typeMapping.empty()) {
|
||||
out << ":]";
|
||||
return;
|
||||
}
|
||||
llvm::interleaveComma(typeMapping, out, [&](const auto &entry) {
|
||||
out << '"' << entry.getKey() << "\" : \"" << entry.getValue() << '"';
|
||||
});
|
||||
out << "]";
|
||||
}
|
||||
|
||||
void printAvailability() {
|
||||
if (!hasMacroParameter("spanAvailability"))
|
||||
return;
|
||||
printSeparator();
|
||||
out << "spanAvailability: ";
|
||||
printAvailabilityOfType("Span");
|
||||
}
|
||||
|
||||
private:
|
||||
bool hasMacroParameter(StringRef ParamName) {
|
||||
for (auto *Param : *SwiftifyImportDecl.parameterList)
|
||||
if (Param->getArgumentName().str() == ParamName)
|
||||
return true;
|
||||
return false;
|
||||
}
|
||||
|
||||
void printAvailabilityOfType(StringRef Name) {
|
||||
ValueDecl *D = getKnownSingleDecl(SwiftContext, Name);
|
||||
out << "\"";
|
||||
llvm::SaveAndRestore<bool> hasAvailbilitySeparatorRestore(firstParam, true);
|
||||
for (auto attr : D->getSemanticAvailableAttrs(/*includingInactive=*/true)) {
|
||||
auto introducedOpt = attr.getIntroduced();
|
||||
if (!introducedOpt.has_value()) continue;
|
||||
printSeparator();
|
||||
out << prettyPlatformString(attr.getPlatform()) << " " << introducedOpt.value();
|
||||
}
|
||||
out << "\"";
|
||||
}
|
||||
|
||||
void printSeparator() {
|
||||
if (!firstParam) {
|
||||
out << ", ";
|
||||
} else {
|
||||
firstParam = false;
|
||||
}
|
||||
}
|
||||
|
||||
void printParamOrReturn(ssize_t pointerIndex) {
|
||||
if (pointerIndex == SELF_PARAM_INDEX)
|
||||
out << ".self";
|
||||
@@ -296,12 +306,25 @@ static StringRef getAttributeName(const clang::CountAttributedType *CAT) {
|
||||
llvm_unreachable("CountAttributedType cannot be ended_by");
|
||||
}
|
||||
}
|
||||
|
||||
template<typename T>
|
||||
static bool getImplicitObjectParamAnnotation(const clang::ObjCMethodDecl* D) {
|
||||
return false; // Only C++ methods have implicit params
|
||||
}
|
||||
|
||||
static size_t getNumParams(const clang::ObjCMethodDecl* D) {
|
||||
return D->param_size();
|
||||
}
|
||||
static size_t getNumParams(const clang::FunctionDecl* D) {
|
||||
return D->getNumParams();
|
||||
}
|
||||
} // namespace
|
||||
|
||||
template<typename T>
|
||||
static bool swiftifyImpl(ClangImporter::Implementation &Self,
|
||||
SwiftifyInfoPrinter &printer,
|
||||
SwiftifyInfoFunctionPrinter &printer,
|
||||
const AbstractFunctionDecl *MappedDecl,
|
||||
const clang::FunctionDecl *ClangDecl) {
|
||||
const T *ClangDecl) {
|
||||
DLOG("Checking " << *ClangDecl << " for bounds and lifetime info\n");
|
||||
|
||||
// FIXME: for private macro generated functions we do not serialize the
|
||||
@@ -310,13 +333,6 @@ static bool swiftifyImpl(ClangImporter::Implementation &Self,
|
||||
ClangDecl->getAccess() == clang::AS_private)
|
||||
return false;
|
||||
|
||||
{
|
||||
UnaliasedInstantiationVisitor visitor;
|
||||
visitor.TraverseType(ClangDecl->getType());
|
||||
if (visitor.hasUnaliasedInstantiation)
|
||||
return false;
|
||||
}
|
||||
|
||||
clang::ASTContext &clangASTContext = Self.getClangASTContext();
|
||||
|
||||
// We only attach the macro if it will produce an overload. Any __counted_by
|
||||
@@ -332,9 +348,10 @@ static bool swiftifyImpl(ClangImporter::Implementation &Self,
|
||||
swiftReturnTy = ctorDecl->getResultInterfaceType();
|
||||
else
|
||||
ABORT("Unexpected AbstractFunctionDecl subclass.");
|
||||
clang::QualType clangReturnTy = ClangDecl->getReturnType();
|
||||
bool returnIsStdSpan = printer.registerStdSpanTypeMapping(
|
||||
swiftReturnTy, ClangDecl->getReturnType());
|
||||
auto *CAT = ClangDecl->getReturnType()->getAs<clang::CountAttributedType>();
|
||||
swiftReturnTy, clangReturnTy);
|
||||
auto *CAT = clangReturnTy->getAs<clang::CountAttributedType>();
|
||||
if (SwiftifiableCAT(clangASTContext, CAT, swiftReturnTy)) {
|
||||
printer.printCountedBy(CAT, SwiftifyInfoPrinter::RETURN_VALUE_INDEX);
|
||||
DLOG(" Found bounds info '" << clang::QualType(CAT, 0) << "' on return value\n");
|
||||
@@ -361,13 +378,13 @@ static bool swiftifyImpl(ClangImporter::Implementation &Self,
|
||||
size_t swiftNumParams = MappedDecl->getParameters()->size() -
|
||||
(ClangDecl->isVariadic() ? 1 : 0);
|
||||
ASSERT((MappedDecl->isImportAsInstanceMember() == isClangInstanceMethod) ==
|
||||
(ClangDecl->getNumParams() == swiftNumParams));
|
||||
(getNumParams(ClangDecl) == swiftNumParams));
|
||||
|
||||
size_t selfParamIndex = MappedDecl->isImportAsInstanceMember()
|
||||
? MappedDecl->getSelfIndex()
|
||||
: ClangDecl->getNumParams();
|
||||
: getNumParams(ClangDecl);
|
||||
for (auto [index, clangParam] : llvm::enumerate(ClangDecl->parameters())) {
|
||||
auto clangParamTy = clangParam->getType();
|
||||
clang::QualType clangParamTy = clangParam->getType();
|
||||
int mappedIndex = index < selfParamIndex ? index :
|
||||
index > selfParamIndex ? index - 1 :
|
||||
SwiftifyInfoPrinter::SELF_PARAM_INDEX;
|
||||
@@ -383,9 +400,8 @@ static bool swiftifyImpl(ClangImporter::Implementation &Self,
|
||||
auto *CAT = clangParamTy->getAs<clang::CountAttributedType>();
|
||||
if (CAT && mappedIndex == SwiftifyInfoPrinter::SELF_PARAM_INDEX) {
|
||||
Self.diagnose(HeaderLoc(clangParam->getLocation()),
|
||||
diag::warn_clang_ignored_bounds_on_self,
|
||||
getAttributeName(CAT));
|
||||
auto swiftName = ClangDecl->getAttr<clang::SwiftNameAttr>();
|
||||
diag::warn_clang_ignored_bounds_on_self, getAttributeName(CAT));
|
||||
auto swiftName = ClangDecl->template getAttr<clang::SwiftNameAttr>();
|
||||
ASSERT(swiftName &&
|
||||
"free function mapped to instance method without swift_name??");
|
||||
Self.diagnose(HeaderLoc(swiftName->getLocation()),
|
||||
@@ -401,7 +417,7 @@ static bool swiftifyImpl(ClangImporter::Implementation &Self,
|
||||
paramHasBoundsInfo |= paramIsStdSpan;
|
||||
|
||||
bool paramHasLifetimeInfo = false;
|
||||
if (clangParam->hasAttr<clang::NoEscapeAttr>()) {
|
||||
if (clangParam->template hasAttr<clang::NoEscapeAttr>()) {
|
||||
DLOG(" Found noescape attribute on parameter '" << *clangParam << "'\n");
|
||||
printer.printNonEscaping(mappedIndex);
|
||||
paramHasLifetimeInfo = true;
|
||||
@@ -435,6 +451,48 @@ static bool swiftifyImpl(ClangImporter::Implementation &Self,
|
||||
return attachMacro;
|
||||
}
|
||||
|
||||
class SwiftifyProtocolInfoPrinter : public SwiftifyInfoPrinter {
|
||||
private:
|
||||
ClangImporter::Implementation &ImporterImpl;
|
||||
|
||||
public:
|
||||
SwiftifyProtocolInfoPrinter(ClangImporter::Implementation &ImporterImpl,
|
||||
clang::ASTContext &ctx, ASTContext &SwiftContext,
|
||||
llvm::raw_svector_ostream &out,
|
||||
MacroDecl &SwiftifyImportDecl,
|
||||
llvm::StringMap<std::string> &typeMapping)
|
||||
: SwiftifyInfoPrinter(ctx, SwiftContext, out, SwiftifyImportDecl, typeMapping),
|
||||
ImporterImpl(ImporterImpl) {}
|
||||
|
||||
bool printMethod(const FuncDecl *Method) {
|
||||
auto ClangDecl = dyn_cast_or_null<clang::ObjCMethodDecl>(Method->getClangDecl());
|
||||
if (!ClangDecl)
|
||||
return false;
|
||||
|
||||
llvm::SmallString<128> paramInfoString;
|
||||
llvm::raw_svector_ostream tmpOut(paramInfoString);
|
||||
|
||||
SwiftifyInfoFunctionPrinter methodPrinter(ctx, SwiftContext, tmpOut,
|
||||
SwiftifyImportDecl, typeMapping);
|
||||
bool hadAttributes = swiftifyImpl(ImporterImpl, methodPrinter, Method, ClangDecl);
|
||||
if (hadAttributes) {
|
||||
printSeparator();
|
||||
out << ".method(signature: \"";
|
||||
printMethodSignature(Method);
|
||||
out << "\", paramInfo: [" << paramInfoString << "])";
|
||||
}
|
||||
return hadAttributes;
|
||||
}
|
||||
|
||||
private:
|
||||
void printMethodSignature(const FuncDecl *Method) {
|
||||
auto options =
|
||||
PrintOptions::printForDiagnostics(AccessLevel::Private, true);
|
||||
StreamPrinter printer(out);
|
||||
Method->print(printer, options);
|
||||
}
|
||||
};
|
||||
|
||||
void ClangImporter::Implementation::swiftify(AbstractFunctionDecl *MappedDecl) {
|
||||
if (!SwiftContext.LangOpts.hasFeature(Feature::SafeInteropWrappers) ||
|
||||
SwiftContext.ClangImporterOpts.DisableSafeInteropWrappers)
|
||||
@@ -443,6 +501,13 @@ void ClangImporter::Implementation::swiftify(AbstractFunctionDecl *MappedDecl) {
|
||||
if (!ClangDecl)
|
||||
return;
|
||||
|
||||
{
|
||||
UnaliasedInstantiationVisitor visitor;
|
||||
visitor.TraverseType(ClangDecl->getType());
|
||||
if (visitor.hasUnaliasedInstantiation)
|
||||
return;
|
||||
}
|
||||
|
||||
MacroDecl *SwiftifyImportDecl = dyn_cast_or_null<MacroDecl>(getKnownSingleDecl(SwiftContext, "_SwiftifyImport"));
|
||||
if (!SwiftifyImportDecl)
|
||||
return;
|
||||
@@ -450,13 +515,16 @@ void ClangImporter::Implementation::swiftify(AbstractFunctionDecl *MappedDecl) {
|
||||
llvm::SmallString<128> MacroString;
|
||||
{
|
||||
llvm::raw_svector_ostream out(MacroString);
|
||||
out << "@_SwiftifyImport";
|
||||
out << "@_SwiftifyImport(";
|
||||
|
||||
SwiftifyInfoPrinter printer(getClangASTContext(), SwiftContext, out, *SwiftifyImportDecl);
|
||||
llvm::StringMap<std::string> typeMapping;
|
||||
SwiftifyInfoFunctionPrinter printer(getClangASTContext(), SwiftContext, out,
|
||||
*SwiftifyImportDecl, typeMapping);
|
||||
if (!swiftifyImpl(*this, printer, MappedDecl, ClangDecl))
|
||||
return;
|
||||
printer.printAvailability();
|
||||
printer.printTypeMapping();
|
||||
out << ")";
|
||||
}
|
||||
|
||||
DLOG("Attaching safe interop macro: " << MacroString << "\n");
|
||||
@@ -479,3 +547,46 @@ void ClangImporter::Implementation::swiftify(AbstractFunctionDecl *MappedDecl) {
|
||||
}
|
||||
}
|
||||
|
||||
void ClangImporter::Implementation::swiftifyProtocol(
|
||||
NominalTypeDecl *MappedDecl) {
|
||||
if (!SwiftContext.LangOpts.hasFeature(Feature::SafeInteropWrappers) ||
|
||||
SwiftContext.ClangImporterOpts.DisableSafeInteropWrappers)
|
||||
return;
|
||||
if (!isa<ProtocolDecl, ClassDecl>(MappedDecl))
|
||||
return;
|
||||
|
||||
MacroDecl *SwiftifyImportDecl = dyn_cast_or_null<MacroDecl>(
|
||||
getKnownSingleDecl(SwiftContext, "_SwiftifyImportProtocol"));
|
||||
if (!SwiftifyImportDecl)
|
||||
return;
|
||||
|
||||
DLOG("Checking " << MappedDecl->getName() << " protocol for methods with bounds and lifetime info\n");
|
||||
llvm::SmallString<128> MacroString;
|
||||
{
|
||||
llvm::raw_svector_ostream out(MacroString);
|
||||
out << "@_SwiftifyImportProtocol(";
|
||||
|
||||
bool hasBoundsAttributes = false;
|
||||
llvm::StringMap<std::string> typeMapping;
|
||||
SwiftifyProtocolInfoPrinter printer(*this, getClangASTContext(),
|
||||
SwiftContext, out, *SwiftifyImportDecl,
|
||||
typeMapping);
|
||||
for (Decl *SwiftMember :
|
||||
cast<IterableDeclContext>(MappedDecl)->getAllMembers()) {
|
||||
FuncDecl *SwiftDecl = dyn_cast<FuncDecl>(SwiftMember);
|
||||
if (!SwiftDecl)
|
||||
continue;
|
||||
hasBoundsAttributes |= printer.printMethod(SwiftDecl);
|
||||
}
|
||||
|
||||
if (!hasBoundsAttributes)
|
||||
return;
|
||||
printer.printAvailability();
|
||||
printer.printTypeMapping();
|
||||
out << ")";
|
||||
}
|
||||
|
||||
DLOG("Attaching safe interop macro: " << MacroString << "\n");
|
||||
importNontrivialAttribute(MappedDecl, MacroString);
|
||||
}
|
||||
|
||||
|
||||
@@ -1808,11 +1808,22 @@ public struct SwiftifyImportProtocolMacro: ExtensionMacro {
|
||||
}
|
||||
let overloads = try arguments.map {
|
||||
let (method, args) = try parseProtocolMacroParam($0, methods: methods)
|
||||
let function = try constructOverloadFunction(
|
||||
let hasVisibilityModifier = method.modifiers.contains {
|
||||
return switch $0.name.trimmed.text {
|
||||
case "open", "public", "package", "internal", "fileprivate", "private": true
|
||||
default: false
|
||||
}
|
||||
}
|
||||
let result = try constructOverloadFunction(
|
||||
forDecl: method, leadingTrivia: Trivia(), args: args,
|
||||
spanAvailability: spanAvailability,
|
||||
typeMappings: typeMappings)
|
||||
return MemberBlockItemSyntax(decl: function)
|
||||
guard let newMethod = result.as(FunctionDeclSyntax.self)?
|
||||
.with(\.modifiers, method.modifiers
|
||||
+ (hasVisibilityModifier ? [] : [DeclModifierSyntax(name: .identifier("public"))])) else {
|
||||
throw RuntimeError("expected FunctionDeclSyntax but got \(result.kind) for \(method.description)")
|
||||
}
|
||||
return MemberBlockItemSyntax(decl: newMethod)
|
||||
}
|
||||
|
||||
return [ExtensionDeclSyntax(extensionKeyword: .identifier("extension"), extendedType: type,
|
||||
|
||||
@@ -1379,6 +1379,7 @@ swift::expandFreestandingMacro(MacroExpansionDecl *med) {
|
||||
return macroSourceFile->getBufferID();
|
||||
}
|
||||
|
||||
|
||||
static SourceFile *evaluateAttachedMacro(MacroDecl *macro, Decl *attachedTo,
|
||||
CustomAttr *attr,
|
||||
bool passParentContext, MacroRole role,
|
||||
@@ -1389,7 +1390,11 @@ static SourceFile *evaluateAttachedMacro(MacroDecl *macro, Decl *attachedTo,
|
||||
dc = attachedTo->getDeclContext();
|
||||
} else if (role == MacroRole::Conformance || role == MacroRole::Extension) {
|
||||
// Conformance macros always expand to extensions at file-scope.
|
||||
dc = attachedTo->getDeclContext()->getParentSourceFile();
|
||||
dc = attachedTo->getDeclContext();
|
||||
if (!isa<ClangModuleUnit>(dc->getModuleScopeContext()))
|
||||
dc = dc->getParentSourceFile();
|
||||
else
|
||||
ASSERT(isa<FileUnit>(dc) && !isa<SourceFile>(dc) && "decls imported from Clang should not have a SourceFile");
|
||||
} else {
|
||||
dc = attachedTo->getInnermostDeclContext();
|
||||
}
|
||||
|
||||
@@ -0,0 +1,178 @@
|
||||
// REQUIRES: swift_feature_SafeInteropWrappers
|
||||
// REQUIRES: swift_feature_LifetimeDependence
|
||||
|
||||
// REQUIRES: foundation
|
||||
|
||||
// RUN: %empty-directory(%t)
|
||||
// RUN: split-file %s %t
|
||||
|
||||
// RUN: %target-swift-frontend -emit-module -plugin-path %swift-plugin-dir -I %t -enable-experimental-feature SafeInteropWrappers -enable-experimental-feature LifetimeDependence %t/test.swift -verify -Xcc -Wno-nullability-completeness
|
||||
// RUN: env SWIFT_BACKTRACE="" %target-swift-frontend -emit-module -plugin-path %swift-plugin-dir -I %t -enable-experimental-feature SafeInteropWrappers -enable-experimental-feature LifetimeDependence %t/test.swift -dump-macro-expansions 2> %t/expansions.out
|
||||
// RUN: %diff %t/expansions.out %t/expansions.expected
|
||||
|
||||
//--- test.h
|
||||
#pragma once
|
||||
|
||||
#include <Foundation/Foundation.h>
|
||||
|
||||
// __counted_by definition inherited from Foundation.h
|
||||
#define __noescape __attribute__((noescape))
|
||||
#define __lifetimebound __attribute__((lifetimebound))
|
||||
|
||||
void foo(int len, int * __counted_by(len) p __noescape);
|
||||
@protocol TestProtocol
|
||||
- (void) bar:(int * __noescape)p _Nullable:(int)asdf;
|
||||
- (void) simple:(int)len :(int * __counted_by(len) __noescape)p;
|
||||
- (void) shared:(int)len :(int * __counted_by(len) __noescape)p1 :(int * __counted_by(len) __noescape)p2;
|
||||
- (void) complexExpr:(int)len :(int) offset :(int * __counted_by(len - offset) __noescape)p;
|
||||
- (void) nullUnspecified:(int)len :(int * __counted_by(len) _Null_unspecified __noescape)p;
|
||||
- (void) nonnull:(int)len :(int * __counted_by(len) _Nonnull __noescape)p;
|
||||
- (void) nullable:(int)len :(int * __counted_by(len) _Nullable __noescape)p;
|
||||
- (int * __counted_by(len)) returnPointer:(int)len : (int * __counted_by(len) _Nullable) __lifetimebound p;
|
||||
- (void) mixedEscapability:(int)len :(int * __counted_by(len) __noescape)p1 :(int * __counted_by(len))p2;
|
||||
@end
|
||||
|
||||
@protocol StaticProtocol
|
||||
+ (void) staticMethod:(int)len :(int * __counted_by(len) __noescape)p;
|
||||
@end
|
||||
|
||||
@interface StaticInterface : NSObject <StaticProtocol> {}
|
||||
@end
|
||||
|
||||
//--- expansions.expected
|
||||
@__swiftmacro_So12TestProtocol015_SwiftifyImportB0fMe_.swift
|
||||
------------------------------
|
||||
extension TestProtocol {
|
||||
/// This is an auto-generated wrapper for safer interop
|
||||
@_alwaysEmitIntoClient @available(visionOS 1.0, tvOS 12.2, watchOS 5.2, iOS 12.2, macOS 10.14.4, *) @_lifetime(p: copy p) @_disfavoredOverload public
|
||||
func simple(_ p: inout MutableSpan<Int32>) {
|
||||
let len = Int32(exactly: p.count)!
|
||||
return unsafe p.withUnsafeMutableBufferPointer { _pPtr in
|
||||
return unsafe simple(len, _pPtr.baseAddress!)
|
||||
}
|
||||
}
|
||||
/// This is an auto-generated wrapper for safer interop
|
||||
@_alwaysEmitIntoClient @available(visionOS 1.0, tvOS 12.2, watchOS 5.2, iOS 12.2, macOS 10.14.4, *) @_lifetime(p1: copy p1) @_lifetime(p2: copy p2) @_disfavoredOverload public
|
||||
func shared(_ p1: inout MutableSpan<Int32>, _ p2: inout MutableSpan<Int32>) {
|
||||
let len = Int32(exactly: p1.count)!
|
||||
if p2.count != len {
|
||||
fatalError("bounds check failure in shared: expected \(len) but got \(p2.count)")
|
||||
}
|
||||
return unsafe p2.withUnsafeMutableBufferPointer { _p2Ptr in
|
||||
return unsafe p1.withUnsafeMutableBufferPointer { _p1Ptr in
|
||||
return unsafe shared(len, _p1Ptr.baseAddress!, _p2Ptr.baseAddress!)
|
||||
}
|
||||
}
|
||||
}
|
||||
/// This is an auto-generated wrapper for safer interop
|
||||
@_alwaysEmitIntoClient @available(visionOS 1.0, tvOS 12.2, watchOS 5.2, iOS 12.2, macOS 10.14.4, *) @_lifetime(p: copy p) @_disfavoredOverload public
|
||||
func complexExpr(_ len: Int32, _ offset: Int32, _ p: inout MutableSpan<Int32>) {
|
||||
let _pCount = p.count
|
||||
if _pCount != len - offset {
|
||||
fatalError("bounds check failure in complexExpr: expected \(len - offset) but got \(_pCount)")
|
||||
}
|
||||
return unsafe p.withUnsafeMutableBufferPointer { _pPtr in
|
||||
return unsafe complexExpr(len, offset, _pPtr.baseAddress!)
|
||||
}
|
||||
}
|
||||
/// This is an auto-generated wrapper for safer interop
|
||||
@_alwaysEmitIntoClient @available(visionOS 1.0, tvOS 12.2, watchOS 5.2, iOS 12.2, macOS 10.14.4, *) @_lifetime(p: copy p) @_disfavoredOverload public
|
||||
func nullUnspecified(_ p: inout MutableSpan<Int32>) {
|
||||
let len = Int32(exactly: p.count)!
|
||||
return unsafe p.withUnsafeMutableBufferPointer { _pPtr in
|
||||
return unsafe nullUnspecified(len, _pPtr.baseAddress!)
|
||||
}
|
||||
}
|
||||
/// This is an auto-generated wrapper for safer interop
|
||||
@_alwaysEmitIntoClient @available(visionOS 1.0, tvOS 12.2, watchOS 5.2, iOS 12.2, macOS 10.14.4, *) @_lifetime(p: copy p) @_disfavoredOverload public
|
||||
func nonnull(_ p: inout MutableSpan<Int32>) {
|
||||
let len = Int32(exactly: p.count)!
|
||||
return unsafe p.withUnsafeMutableBufferPointer { _pPtr in
|
||||
return unsafe nonnull(len, _pPtr.baseAddress!)
|
||||
}
|
||||
}
|
||||
/// This is an auto-generated wrapper for safer interop
|
||||
@_alwaysEmitIntoClient @available(visionOS 1.0, tvOS 12.2, watchOS 5.2, iOS 12.2, macOS 10.14.4, *) @_lifetime(p: copy p) @_disfavoredOverload public
|
||||
func nullable(_ p: inout MutableSpan<Int32>?) {
|
||||
let len = Int32(exactly: p?.count ?? 0)!
|
||||
return { () in
|
||||
return if p == nil {
|
||||
unsafe nullable(len, nil)
|
||||
} else {
|
||||
unsafe p!.withUnsafeMutableBufferPointer { _pPtr in
|
||||
return unsafe nullable(len, _pPtr.baseAddress)
|
||||
}
|
||||
}
|
||||
}()
|
||||
}
|
||||
/// This is an auto-generated wrapper for safer interop
|
||||
@_alwaysEmitIntoClient @available(visionOS 1.0, tvOS 12.2, watchOS 5.2, iOS 12.2, macOS 10.14.4, *) @_lifetime(copy p) @_lifetime(p: copy p) @_disfavoredOverload public
|
||||
func returnPointer(_ p: inout MutableSpan<Int32>?) -> MutableSpan<Int32> {
|
||||
let len = Int32(exactly: p?.count ?? 0)!
|
||||
return unsafe _swiftifyOverrideLifetime(MutableSpan<Int32>(_unsafeStart: { () in
|
||||
return if p == nil {
|
||||
unsafe returnPointer(len, nil)
|
||||
} else {
|
||||
unsafe p!.withUnsafeMutableBufferPointer { _pPtr in
|
||||
return unsafe returnPointer(len, _pPtr.baseAddress)
|
||||
}
|
||||
}
|
||||
}(), count: Int(len)), copying: ())
|
||||
}
|
||||
/// This is an auto-generated wrapper for safer interop
|
||||
@_alwaysEmitIntoClient @available(visionOS 1.0, tvOS 12.2, watchOS 5.2, iOS 12.2, macOS 10.14.4, *) @_lifetime(p1: copy p1) @_disfavoredOverload public
|
||||
func mixedEscapability(_ p1: inout MutableSpan<Int32>, _ p2: UnsafeMutableBufferPointer<Int32>) {
|
||||
let len = Int32(exactly: p1.count)!
|
||||
if p2.count != len {
|
||||
fatalError("bounds check failure in mixedEscapability: expected \(len) but got \(p2.count)")
|
||||
}
|
||||
return unsafe p1.withUnsafeMutableBufferPointer { _p1Ptr in
|
||||
return unsafe mixedEscapability(len, _p1Ptr.baseAddress!, p2.baseAddress!)
|
||||
}
|
||||
}
|
||||
}
|
||||
------------------------------
|
||||
@__swiftmacro_So14StaticProtocol015_SwiftifyImportB0fMe_.swift
|
||||
------------------------------
|
||||
extension StaticProtocol {
|
||||
/// This is an auto-generated wrapper for safer interop
|
||||
@_alwaysEmitIntoClient @available(visionOS 1.0, tvOS 12.2, watchOS 5.2, iOS 12.2, macOS 10.14.4, *) @_lifetime(p: copy p) @_disfavoredOverload
|
||||
static public func staticMethod(_ p: inout MutableSpan<Int32>) {
|
||||
let len = Int32(exactly: p.count)!
|
||||
return unsafe p.withUnsafeMutableBufferPointer { _pPtr in
|
||||
return unsafe staticMethod(len, _pPtr.baseAddress!)
|
||||
}
|
||||
}
|
||||
}
|
||||
------------------------------
|
||||
@__swiftmacro_So3foo15_SwiftifyImportfMp_.swift
|
||||
------------------------------
|
||||
/// This is an auto-generated wrapper for safer interop
|
||||
@_alwaysEmitIntoClient @available(visionOS 1.0, tvOS 12.2, watchOS 5.2, iOS 12.2, macOS 10.14.4, *) @_lifetime(p: copy p) @_disfavoredOverload public func foo(_ p: inout MutableSpan<Int32>) {
|
||||
let len = Int32(exactly: p.count)!
|
||||
return unsafe p.withUnsafeMutableBufferPointer { _pPtr in
|
||||
return unsafe foo(len, _pPtr.baseAddress!)
|
||||
}
|
||||
}
|
||||
------------------------------
|
||||
//--- test.swift
|
||||
import TestClang
|
||||
|
||||
@inlinable
|
||||
public func call(p: inout MutableSpan<CInt>, p2: inout MutableSpan<CInt>, p3: inout MutableSpan<CInt>?, a: TestProtocol) {
|
||||
a.simple(&p)
|
||||
a.shared(&p, &p2)
|
||||
a.complexExpr(2, 3, &p)
|
||||
a.nullUnspecified(&p)
|
||||
a.nonnull(&p)
|
||||
a.nullable(&p3)
|
||||
let _: MutableSpan<CInt> = a.returnPointer(&p3)
|
||||
StaticInterface.staticMethod(&p2)
|
||||
foo(&p)
|
||||
}
|
||||
|
||||
//--- module.modulemap
|
||||
module TestClang {
|
||||
header "test.h"
|
||||
export *
|
||||
}
|
||||
133
test/Interop/ObjC/swiftify-import/counted-by-protocol.swift
Normal file
133
test/Interop/ObjC/swiftify-import/counted-by-protocol.swift
Normal file
@@ -0,0 +1,133 @@
|
||||
// REQUIRES: swift_feature_SafeInteropWrappers
|
||||
|
||||
// RUN: %empty-directory(%t)
|
||||
// RUN: split-file %s %t
|
||||
|
||||
// RUN: %target-swift-frontend -emit-module -plugin-path %swift-plugin-dir -o %t/CountedByProtocol.swiftmodule -I %t/Inputs -enable-experimental-feature SafeInteropWrappers %t/counted-by-protocol.swift -verify -Xcc -Wno-nullability-completeness
|
||||
// RUN: env SWIFT_BACKTRACE="" %target-swift-frontend -emit-module -plugin-path %swift-plugin-dir -o %t/CountedByProtocol.swiftmodule -I %t/Inputs -enable-experimental-feature SafeInteropWrappers %t/counted-by-protocol.swift -dump-macro-expansions 2> %t/expansions.out
|
||||
// RUN: %diff %t/expansions.out %t/expansions.expected
|
||||
|
||||
//--- Inputs/module.modulemap
|
||||
module CountedByProtocolClang {
|
||||
header "counted-by-protocol.h"
|
||||
export *
|
||||
}
|
||||
|
||||
//--- Inputs/counted-by-protocol.h
|
||||
#pragma once
|
||||
|
||||
#define __counted_by(x) __attribute__((__counted_by__(x)))
|
||||
|
||||
int foo(int len, int * __counted_by(len) p);
|
||||
@protocol CountedByProtocol
|
||||
- (void) simple:(int)len :(int * __counted_by(len))p;
|
||||
- (void) shared:(int)len :(int * __counted_by(len))p1 :(int * __counted_by(len))p2;
|
||||
- (void) complexExpr:(int)len :(int) offset :(int * __counted_by(len - offset))p;
|
||||
- (void) nullUnspecified:(int)len :(int * __counted_by(len) _Null_unspecified)p;
|
||||
- (void) nonnull:(int)len :(int * __counted_by(len) _Nonnull)p;
|
||||
- (void) nullable:(int)len :(int * __counted_by(len) _Nullable)p;
|
||||
- (int * __counted_by(len)) returnPointer:(int)len;
|
||||
|
||||
+ (void) staticMethod:(int)len :(int * __counted_by(len))p;
|
||||
@end
|
||||
|
||||
__attribute__((swift_attr("@_SwiftifyImportProtocol(.method(signature: \"func swiftAttr(_ len: Int32, _ p: UnsafeMutablePointer<Int32>!)\", paramInfo: [.countedBy(pointer: .param(2), count: \"len\")]))")))
|
||||
@protocol SwiftAttrProtocol
|
||||
- (void)swiftAttr:(int)len :(int *)p;
|
||||
@end
|
||||
|
||||
//--- expansions.expected
|
||||
@__swiftmacro_So17CountedByProtocol015_SwiftifyImportC0fMe_.swift
|
||||
------------------------------
|
||||
extension CountedByProtocol {
|
||||
/// This is an auto-generated wrapper for safer interop
|
||||
@_alwaysEmitIntoClient @_disfavoredOverload public
|
||||
func simple(_ p: UnsafeMutableBufferPointer<Int32>) {
|
||||
let len = Int32(exactly: p.count)!
|
||||
return unsafe simple(len, p.baseAddress!)
|
||||
}
|
||||
/// This is an auto-generated wrapper for safer interop
|
||||
@_alwaysEmitIntoClient @_disfavoredOverload public
|
||||
func shared(_ p1: UnsafeMutableBufferPointer<Int32>, _ p2: UnsafeMutableBufferPointer<Int32>) {
|
||||
let len = Int32(exactly: p1.count)!
|
||||
if p2.count != len {
|
||||
fatalError("bounds check failure in shared: expected \(len) but got \(p2.count)")
|
||||
}
|
||||
return unsafe shared(len, p1.baseAddress!, p2.baseAddress!)
|
||||
}
|
||||
/// This is an auto-generated wrapper for safer interop
|
||||
@_alwaysEmitIntoClient @_disfavoredOverload public
|
||||
func complexExpr(_ len: Int32, _ offset: Int32, _ p: UnsafeMutableBufferPointer<Int32>) {
|
||||
let _pCount = p.count
|
||||
if _pCount != len - offset {
|
||||
fatalError("bounds check failure in complexExpr: expected \(len - offset) but got \(_pCount)")
|
||||
}
|
||||
return unsafe complexExpr(len, offset, p.baseAddress!)
|
||||
}
|
||||
/// This is an auto-generated wrapper for safer interop
|
||||
@_alwaysEmitIntoClient @_disfavoredOverload public
|
||||
func nullUnspecified(_ p: UnsafeMutableBufferPointer<Int32>) {
|
||||
let len = Int32(exactly: p.count)!
|
||||
return unsafe nullUnspecified(len, p.baseAddress!)
|
||||
}
|
||||
/// This is an auto-generated wrapper for safer interop
|
||||
@_alwaysEmitIntoClient @_disfavoredOverload public
|
||||
func nonnull(_ p: UnsafeMutableBufferPointer<Int32>) {
|
||||
let len = Int32(exactly: p.count)!
|
||||
return unsafe nonnull(len, p.baseAddress!)
|
||||
}
|
||||
/// This is an auto-generated wrapper for safer interop
|
||||
@_alwaysEmitIntoClient @_disfavoredOverload public
|
||||
func nullable(_ p: UnsafeMutableBufferPointer<Int32>?) {
|
||||
let len = Int32(exactly: unsafe p?.count ?? 0)!
|
||||
return unsafe nullable(len, p?.baseAddress)
|
||||
}
|
||||
/// This is an auto-generated wrapper for safer interop
|
||||
@_alwaysEmitIntoClient @_disfavoredOverload public
|
||||
func returnPointer(_ len: Int32) -> UnsafeMutableBufferPointer<Int32> {
|
||||
return unsafe UnsafeMutableBufferPointer<Int32>(start: unsafe returnPointer(len), count: Int(len))
|
||||
}
|
||||
/// This is an auto-generated wrapper for safer interop
|
||||
@_alwaysEmitIntoClient @_disfavoredOverload
|
||||
static public func staticMethod(_ p: UnsafeMutableBufferPointer<Int32>) {
|
||||
let len = Int32(exactly: p.count)!
|
||||
return unsafe staticMethod(len, p.baseAddress!)
|
||||
}
|
||||
}
|
||||
------------------------------
|
||||
@__swiftmacro_So17SwiftAttrProtocol015_SwiftifyImportC0fMe_.swift
|
||||
------------------------------
|
||||
extension SwiftAttrProtocol {
|
||||
/// This is an auto-generated wrapper for safer interop
|
||||
@_alwaysEmitIntoClient @_disfavoredOverload public
|
||||
func swiftAttr(_ p: UnsafeMutableBufferPointer<Int32>) {
|
||||
let len = Int32(exactly: p.count)!
|
||||
return unsafe swiftAttr(len, p.baseAddress!)
|
||||
}
|
||||
}
|
||||
------------------------------
|
||||
@__swiftmacro_So3foo15_SwiftifyImportfMp_.swift
|
||||
------------------------------
|
||||
/// This is an auto-generated wrapper for safer interop
|
||||
@_alwaysEmitIntoClient @_disfavoredOverload public func foo(_ p: UnsafeMutableBufferPointer<Int32>) -> Int32 {
|
||||
let len = Int32(exactly: p.count)!
|
||||
return unsafe foo(len, p.baseAddress!)
|
||||
}
|
||||
------------------------------
|
||||
//--- counted-by-protocol.swift
|
||||
import CountedByProtocolClang
|
||||
|
||||
@inlinable
|
||||
public func call(p: UnsafeMutableBufferPointer<CInt>, x: CInt, y: CInt, a: CountedByProtocol, b: SwiftAttrProtocol) {
|
||||
a.simple(p)
|
||||
a.shared(p, p)
|
||||
a.complexExpr(x, y, p)
|
||||
a.nullUnspecified(p)
|
||||
a.nonnull(p)
|
||||
a.nullable(p)
|
||||
let _: UnsafeMutableBufferPointer<CInt> = a.returnPointer(x)
|
||||
let r2 = a.returnPointer(x)
|
||||
let _: UnsafeMutablePointer<CInt>? = r2 // make sure the original is the favored overload
|
||||
b.swiftAttr(p)
|
||||
let _ = foo(p)
|
||||
}
|
||||
97
test/Interop/ObjC/swiftify-import/negative.swift
Normal file
97
test/Interop/ObjC/swiftify-import/negative.swift
Normal file
@@ -0,0 +1,97 @@
|
||||
// REQUIRES: swift_feature_SafeInteropWrappers
|
||||
|
||||
// RUN: %empty-directory(%t)
|
||||
// RUN: split-file %s %t
|
||||
|
||||
// RUN: %target-swift-frontend -emit-module -plugin-path %swift-plugin-dir -I %t -enable-experimental-feature SafeInteropWrappers %t/test.swift -verify -Xcc -Wno-nullability-completeness
|
||||
// RUN: env SWIFT_BACKTRACE="" %target-swift-frontend -emit-module -plugin-path %swift-plugin-dir -I %t -enable-experimental-feature SafeInteropWrappers %t/test.swift -dump-macro-expansions 2> %t/expansions.out
|
||||
// RUN: %diff %t/expansions.out %t/expansions.expected
|
||||
|
||||
//--- test.h
|
||||
#pragma once
|
||||
|
||||
#define __counted_by(x) __attribute__((__counted_by__(x)))
|
||||
|
||||
@protocol NoBounds
|
||||
- (void) ignore;
|
||||
@end
|
||||
|
||||
@protocol NoYesNo
|
||||
- (void) ignore;
|
||||
- (void) simple:(int)len :(int * __counted_by(len))p;
|
||||
- (void) ignore2;
|
||||
@end
|
||||
|
||||
@protocol YesNo
|
||||
- (void) simple:(int)len :(int * __counted_by(len))p;
|
||||
- (void) ignore;
|
||||
@end
|
||||
|
||||
@protocol YesNoYes
|
||||
- (void) simple:(int)len :(int * __counted_by(len))p;
|
||||
- (void) ignore;
|
||||
- (void) simple2:(int)len :(int * __counted_by(len))p;
|
||||
@end
|
||||
|
||||
//--- expansions.expected
|
||||
@__swiftmacro_So05NoYesA023_SwiftifyImportProtocolfMe_.swift
|
||||
------------------------------
|
||||
extension NoYesNo {
|
||||
/// This is an auto-generated wrapper for safer interop
|
||||
@_alwaysEmitIntoClient @_disfavoredOverload public
|
||||
func simple(_ p: UnsafeMutableBufferPointer<Int32>) {
|
||||
let len = Int32(exactly: p.count)!
|
||||
return unsafe simple(len, p.baseAddress!)
|
||||
}
|
||||
}
|
||||
------------------------------
|
||||
@__swiftmacro_So5YesNo23_SwiftifyImportProtocolfMe_.swift
|
||||
------------------------------
|
||||
extension YesNo {
|
||||
/// This is an auto-generated wrapper for safer interop
|
||||
@_alwaysEmitIntoClient @_disfavoredOverload public
|
||||
func simple(_ p: UnsafeMutableBufferPointer<Int32>) {
|
||||
let len = Int32(exactly: p.count)!
|
||||
return unsafe simple(len, p.baseAddress!)
|
||||
}
|
||||
}
|
||||
------------------------------
|
||||
@__swiftmacro_So05YesNoA023_SwiftifyImportProtocolfMe_.swift
|
||||
------------------------------
|
||||
extension YesNoYes {
|
||||
/// This is an auto-generated wrapper for safer interop
|
||||
@_alwaysEmitIntoClient @_disfavoredOverload public
|
||||
func simple(_ p: UnsafeMutableBufferPointer<Int32>) {
|
||||
let len = Int32(exactly: p.count)!
|
||||
return unsafe simple(len, p.baseAddress!)
|
||||
}
|
||||
/// This is an auto-generated wrapper for safer interop
|
||||
@_alwaysEmitIntoClient @_disfavoredOverload public
|
||||
func simple2(_ p: UnsafeMutableBufferPointer<Int32>) {
|
||||
let len = Int32(exactly: p.count)!
|
||||
return unsafe simple2(len, p.baseAddress!)
|
||||
}
|
||||
}
|
||||
------------------------------
|
||||
//--- test.swift
|
||||
import TestClang
|
||||
|
||||
@inlinable
|
||||
public func call(p: UnsafeMutableBufferPointer<CInt>, x: NoBounds, y: NoYesNo, z: YesNo, å: YesNoYes) {
|
||||
x.ignore()
|
||||
y.ignore()
|
||||
y.simple(p)
|
||||
z.ignore()
|
||||
z.simple(p)
|
||||
å.ignore()
|
||||
å.simple(p)
|
||||
å.simple2(p)
|
||||
}
|
||||
|
||||
//--- module.modulemap
|
||||
module TestClang {
|
||||
header "test.h"
|
||||
export *
|
||||
}
|
||||
|
||||
|
||||
@@ -42,7 +42,7 @@ protocol OverloadedProtocol {
|
||||
------------------------------
|
||||
extension SimpleProtocol {
|
||||
/// This is an auto-generated wrapper for safer interop
|
||||
@_alwaysEmitIntoClient @_disfavoredOverload
|
||||
@_alwaysEmitIntoClient @_disfavoredOverload public
|
||||
func myFunc(_ ptr: UnsafeBufferPointer<CInt>) {
|
||||
let len = CInt(exactly: ptr.count)!
|
||||
return unsafe myFunc(ptr.baseAddress!, len)
|
||||
@@ -53,7 +53,7 @@ extension SimpleProtocol {
|
||||
------------------------------
|
||||
extension SpanProtocol {
|
||||
/// This is an auto-generated wrapper for safer interop
|
||||
@_alwaysEmitIntoClient @_disfavoredOverload
|
||||
@_alwaysEmitIntoClient @_disfavoredOverload public
|
||||
func foo(_ ptr: Span<CInt>) {
|
||||
let len = CInt(exactly: ptr.count)!
|
||||
return unsafe ptr.withUnsafeBufferPointer { _ptrPtr in
|
||||
@@ -61,7 +61,7 @@ extension SpanProtocol {
|
||||
}
|
||||
}
|
||||
/// This is an auto-generated wrapper for safer interop
|
||||
@_alwaysEmitIntoClient @_lifetime(borrow self) @_disfavoredOverload
|
||||
@_alwaysEmitIntoClient @_lifetime(borrow self) @_disfavoredOverload public
|
||||
func bar(_ len: CInt) -> Span<CInt> {
|
||||
return unsafe _swiftifyOverrideLifetime(Span<CInt>(_unsafeStart: unsafe bar(len), count: Int(len)), copying: ())
|
||||
}
|
||||
@@ -71,7 +71,7 @@ extension SpanProtocol {
|
||||
------------------------------
|
||||
extension MixedProtocol {
|
||||
/// This is an auto-generated wrapper for safer interop
|
||||
@_alwaysEmitIntoClient @_disfavoredOverload
|
||||
@_alwaysEmitIntoClient @_disfavoredOverload public
|
||||
/// Some doc comment
|
||||
func foo(_ ptr: Span<CInt>) {
|
||||
let len = CInt(exactly: ptr.count)!
|
||||
@@ -80,7 +80,7 @@ extension MixedProtocol {
|
||||
}
|
||||
}
|
||||
/// This is an auto-generated wrapper for safer interop
|
||||
@_alwaysEmitIntoClient @_disfavoredOverload
|
||||
@_alwaysEmitIntoClient @_disfavoredOverload public
|
||||
func bar(_ ptr: UnsafeBufferPointer<CInt>) {
|
||||
let len = CInt(exactly: ptr.count)!
|
||||
return unsafe bar(ptr.baseAddress!, len)
|
||||
@@ -91,13 +91,13 @@ extension MixedProtocol {
|
||||
------------------------------
|
||||
extension OverloadedProtocol {
|
||||
/// This is an auto-generated wrapper for safer interop
|
||||
@_alwaysEmitIntoClient @_disfavoredOverload
|
||||
@_alwaysEmitIntoClient @_disfavoredOverload public
|
||||
func foo(_ ptr: UnsafeBufferPointer<CInt>) {
|
||||
let len1 = CInt(exactly: ptr.count)!
|
||||
return unsafe foo(ptr.baseAddress!, len1)
|
||||
}
|
||||
/// This is an auto-generated wrapper for safer interop
|
||||
@_alwaysEmitIntoClient @_disfavoredOverload
|
||||
@_alwaysEmitIntoClient @_disfavoredOverload public
|
||||
func foo(bar: UnsafeBufferPointer<CInt>) {
|
||||
let len2 = CInt(exactly: bar.count)!
|
||||
return unsafe foo(bar: bar.baseAddress!, len2)
|
||||
|
||||
Reference in New Issue
Block a user