Start fleshing out RemoteAST's storage-offset API.

This commit is contained in:
John McCall
2016-04-26 16:21:59 -07:00
parent 590d41c00a
commit 312aa06901
4 changed files with 70 additions and 23 deletions

View File

@@ -318,14 +318,9 @@ template <> struct Failure::ArgTypesForFailureKind<Failure::KIND##_t> { \
};
#include "swift/Remote/FailureKinds.def"
template <>
struct Failure::IsAcceptableArgType<Failure::ArgType_String, const char *> {
static constexpr bool value = true;
};
template <>
struct Failure::IsAcceptableArgType<Failure::ArgType_String, std::string> {
static constexpr bool value = true;
template <class T>
struct Failure::IsAcceptableArgType<Failure::ArgType_String, T> {
static constexpr bool value = std::is_convertible<T, std::string>::value;
};
template <>

View File

@@ -13,9 +13,16 @@
// FAILURE(KIND, TEXT, ARGTYS)
FAILURE(Unknown, "an unknown failure occurred", ())
FAILURE(BadArgument, "the API was called with a bad argument", ())
FAILURE(Memory, "an unknown failure occurred while reading %0 at address %1",
(String, Address))
FAILURE(DependentArgument,
"API was called with a dependent type", ())
FAILURE(TypeHasNoSuchMember,
"type has no member named '%0'", (String))
FAILURE(CouldNotResolveTypeDecl,
"could not resolve a type with mangled name '%0'", (String))

View File

@@ -182,12 +182,22 @@ public:
getDeclForRemoteNominalTypeDescriptor(remote::RemoteAddress address);
/// Given a type in the local AST, try to resolve the offset of its
/// property with the given name.
/// member with the given name. This supports:
///
/// This may fail by returning an empty optional. Failure may indicate
/// that an offset for the property could not be resolved, or it may
/// simply indicate that the property has a non-zero offset.
Result<uint64_t> getOffsetForProperty(Type type, StringRef propertyName);
/// - stored properties of structs
/// - stored properties of classes
/// - elements of tuples
///
/// Failure may indicate that an offset for the property could not be
/// resolved, or it may simply indicate that the property is not laid
/// out at a known offset.
///
/// If the caller has the address of type metadata for the type, it may
/// pass it in; this may allow the implementation to compute an offset in
/// situations where it otherwise cannot.
Result<uint64_t> getOffsetOfMember(Type type,
remote::RemoteAddress optMetadataAddress,
StringRef memberName);
};
} // end namespace remoteAST

View File

@@ -617,8 +617,48 @@ public:
getKindForRemoteTypeMetadata(RemoteAddress metadata) = 0;
virtual Result<NominalTypeDecl*>
getDeclForRemoteNominalTypeDescriptor(RemoteAddress descriptor) = 0;
virtual Result<uint64_t>
getOffsetForProperty(Type type, StringRef propertyName) = 0;
Result<uint64_t>
getOffsetOfMember(Type type, RemoteAddress optMetadata, StringRef memberName){
// Sanity check: obviously invalid arguments.
if (!type || memberName.empty())
return Result<uint64_t>::emplaceFailure(Failure::BadArgument);
// Sanity check: if the caller gave us a dependent type, there's no way
// we can handle that.
if (type->hasTypeParameter() || type->hasArchetype())
return Result<uint64_t>::emplaceFailure(Failure::DependentArgument);
// Split into cases.
if (auto typeDecl = type->getNominalOrBoundGenericNominal()) {
return getOffsetOfMember(type, typeDecl, optMetadata, memberName);
} else if (auto tupleType = type->getAs<TupleType>()) {
return getOffsetOfMember(tupleType, optMetadata, memberName);
} else {
return Result<uint64_t>::emplaceFailure(Failure::TypeHasNoSuchMember,
memberName);
}
}
Result<uint64_t>
getOffsetOfMember(Type type, NominalTypeDecl *typeDecl,
RemoteAddress optMetadata, StringRef memberName) {
// FIXME
return Result<uint64_t>::emplaceFailure(Failure::Unknown);
}
Result<uint64_t>
getOffsetOfMember(TupleType *type, RemoteAddress optMetadata,
StringRef memberName) {
// Check that the member "name" is a valid index into the tuple.
unsigned index;
if (memberName.getAsInteger(10, index) || index >= type->getNumElements())
return Result<uint64_t>::emplaceFailure(Failure::TypeHasNoSuchMember,
memberName);
// FIXME
return Result<uint64_t>::emplaceFailure(Failure::Unknown);
}
};
/// A template for generating concrete implementations of the
@@ -660,12 +700,6 @@ public:
return getBuilder().template getFailureAsResult<NominalTypeDecl*>(
Failure::Unknown);
}
Result<uint64_t>
getOffsetForProperty(Type type, StringRef propertyName) override {
// TODO
return Result<uint64_t>::emplaceFailure(Failure::Unknown);
}
};
} // end anonymous namespace
@@ -713,6 +747,7 @@ RemoteASTContext::getDeclForRemoteNominalTypeDescriptor(RemoteAddress address) {
}
Result<uint64_t>
RemoteASTContext::getOffsetForProperty(Type type, StringRef propertyName) {
return asImpl(Impl)->getOffsetForProperty(type, propertyName);
RemoteASTContext::getOffsetOfMember(Type type, RemoteAddress optMetadata,
StringRef memberName) {
return asImpl(Impl)->getOffsetOfMember(type, optMetadata, memberName);
}