Separate underlying storage and location kind in SILLocation and

remove the mixed concept that was SILFileLocation.
Also add support for a third type of underlying storage that will be used
for deserialized debug lcoations from textual SIL.

NFC

<rdar://problem/22706994>
This commit is contained in:
Adrian Prantl
2016-02-19 11:16:38 -08:00
parent f560f3caac
commit 40c7a1abee
14 changed files with 218 additions and 205 deletions

View File

@@ -65,7 +65,7 @@ private:
typedef llvm::PointerUnion4<Stmt*, Expr*, Decl*, Pattern*> ASTNodeTy;
public:
enum LocationKind {
enum LocationKind : unsigned {
// FIXME: NoneKind is to be removed.
NoneKind = 0,
RegularKind = 1,
@@ -74,29 +74,53 @@ public:
InlinedKind = 4,
MandatoryInlinedKind = 5,
CleanupKind = 6,
ArtificialUnreachableKind = 7,
SILFileKind = 8
ArtificialUnreachableKind = 7
};
protected:
/// Primary AST location, always used for diagnostics.
ASTNodeTy ASTNode;
enum StorageKind : unsigned {
UnknownKind = 0,
ASTNodeKind = 1 << 3,
SILFileKind = 1 << 4,
DebugInfoKind = 1 << 3 | 1 << 4
};
union SpecificLoc {
SpecificLoc() : DebugLoc() {}
/// If coming from a .sil file, this is the location in the .sil file.
SourceLoc SILFileSourceLoc;
typedef struct {
unsigned Line = 0, Col = 0;
const char *Filename = nullptr;
} DebugLoc;
protected:
union UnderlyingLocation {
UnderlyingLocation() : DebugInfoLoc({}) {}
UnderlyingLocation(ASTNodeTy N) : ASTNode(N) {}
UnderlyingLocation(SourceLoc L) : SILFileLoc(L) {}
struct ASTNodeLoc {
ASTNodeLoc(ASTNodeTy N) : Primary(N) {}
/// Primary AST location, always used for diagnostics.
ASTNodeTy Primary;
/// Sometimes the location for diagnostics needs to be
/// different than the one used to emit the line table. If
/// HasDebugLoc is set, this is used for the debug info.
ASTNodeTy DebugLoc;
} SpecificLoc;
ASTNodeTy ForDebugger;
} ASTNode;
/// A location inside a textual .sil file.
SourceLoc SILFileLoc;
/// A deserialized source location.
DebugLoc DebugInfoLoc;
} Loc;
/// The kind of this SIL location.
unsigned KindData;
enum {
BaseBits = 4, BaseMask = 0xF,
LocationKindBits = 3,
LocationKindMask = 7,
StorageKindBits = 2,
StorageKindMask = (1 << 3) | (1 << 4),
SpecialFlagsMask = ~ (LocationKindMask | StorageKindMask),
/// Used to mark this instruction as part of auto-generated
/// code block.
@@ -106,7 +130,8 @@ protected:
/// represent this SILLocation. For example, when the host instruction
/// is known to correspond to the beginning or the end of the source
/// range of the ASTNode.
PointsToStartBit = 6, PointsToEndBit = 7,
PointsToStartBit = 6,
PointsToEndBit = 7,
/// Used to notify that this instruction belongs to the top-
/// level (module) scope.
@@ -115,14 +140,7 @@ protected:
IsInTopLevel = 8,
/// Marks this instruction as belonging to the function prologue.
IsInPrologue = 9,
/// Indicates that SILFileSourceLoc is present.
HasSILFileSourceLoc = 10,
/// Indicates that DebugLoc should be used for emitting debug info.
HasDebugLoc = 11
IsInPrologue = 9
};
template <typename T>
@@ -133,7 +151,8 @@ protected:
template <typename T>
bool isNode(ASTNodeTy Node) const {
if (ASTNode.is<typename base_type<T>::type*>())
assert(isASTNode());
if (Loc.ASTNode.Primary.is<typename base_type<T>::type*>())
return isa<T>(Node.get<typename base_type<T>::type*>());
return false;
}
@@ -147,22 +166,40 @@ protected:
/// @{
/// This constructor is used to support getAs operation.
SILLocation() {}
SILLocation(LocationKind K, unsigned Flags = 0)
: KindData(unsigned(K) | Flags) {}
SILLocation() { assert(Loc.DebugInfoLoc.Line == 0); }
SILLocation(LocationKind K, unsigned Flags = 0) : KindData(K | Flags) {
assert(Loc.DebugInfoLoc.Line == 0);
}
SILLocation(Stmt *S, LocationKind K, unsigned Flags = 0)
: ASTNode(S), KindData(unsigned(K) | Flags) {}
: Loc(S), KindData(K | Flags) {
setStorageKind(ASTNodeKind);
assert(isASTNode());
}
SILLocation(Expr *E, LocationKind K, unsigned Flags = 0)
: ASTNode(E), KindData(unsigned(K) | Flags) {}
: Loc(E), KindData(K | Flags) {
setStorageKind(ASTNodeKind);
assert(isASTNode());
}
SILLocation(Decl *D, LocationKind K, unsigned Flags = 0)
: ASTNode(D), KindData(unsigned(K) | Flags) {}
: Loc(D), KindData(K | Flags) {
setStorageKind(ASTNodeKind);
assert(isASTNode());
}
SILLocation(Pattern *P, LocationKind K, unsigned Flags = 0)
: ASTNode(P), KindData(unsigned(K) | Flags) {}
: Loc(P), KindData(K | Flags) {
setStorageKind(ASTNodeKind);
assert(isASTNode());
}
SILLocation(SourceLoc L, LocationKind K, unsigned Flags = 0)
: Loc(L), KindData(K | Flags) {
setStorageKind(SILFileKind);
assert(isSILFile());
}
/// @}
private:
@@ -171,9 +208,12 @@ private:
friend class InlinedLocation;
friend class CleanupLocation;
void setKind(LocationKind K) { KindData |= (K & BaseMask); }
unsigned getSpecialFlags() const { return unsigned(KindData) & ~BaseMask; }
void setSpecialFlags(unsigned Flags) { KindData |= (Flags & ~BaseMask); }
void setLocationKind(LocationKind K) { KindData |= (K & LocationKindMask); }
void setStorageKind(StorageKind K) { KindData |= (K & StorageKindMask); }
unsigned getSpecialFlags() const { return KindData & SpecialFlagsMask; }
void setSpecialFlags(unsigned Flags) {
KindData |= (Flags & SpecialFlagsMask);
}
SourceLoc getSourceLoc(ASTNodeTy N) const;
SourceLoc getStartSourceLoc(ASTNodeTy N) const;
@@ -184,22 +224,43 @@ public:
/// When an ASTNode gets implicitly converted into a SILLocation we
/// construct a RegularLocation. Since RegularLocations represent the majority
/// of locations, this greatly simplifies the user code.
SILLocation(Stmt *S) : ASTNode(S), KindData(RegularKind) {}
SILLocation(Expr *E) : ASTNode(E), KindData(RegularKind) {}
SILLocation(Decl *D) : ASTNode(D), KindData(RegularKind) {}
SILLocation(Pattern *P) : ASTNode(P), KindData(RegularKind) {}
SILLocation(Stmt *S) : Loc(S), KindData(RegularKind) {
setStorageKind(ASTNodeKind);
assert(isASTNode());
}
SILLocation(Expr *E) : Loc(E), KindData(RegularKind) {
setStorageKind(ASTNodeKind);
assert(isASTNode());
}
SILLocation(Decl *D) : Loc(D), KindData(RegularKind) {
setStorageKind(ASTNodeKind);
assert(isASTNode());
}
SILLocation(Pattern *P) : Loc(P), KindData(RegularKind) {
setStorageKind(ASTNodeKind);
assert(isASTNode());
}
/// Check if the location wraps an AST node or a valid SIL file
/// location.
///
/// Artificial locations and the top-level module locations will be null.
bool isNull() const {
if (hasSILFileSourceLoc())
return SpecificLoc.SILFileSourceLoc.isInvalid();
return ASTNode.isNull();
switch (getStorageKind()) {
case ASTNodeKind: return Loc.ASTNode.Primary.isNull();
case DebugInfoKind: return Loc.DebugInfoLoc.Filename;
case SILFileKind: return Loc.SILFileLoc.isInvalid();
default: return true;
}
}
explicit operator bool() const { return !isNull(); }
/// Return whether this location is backed by an AST node.
bool isASTNode() const { return getStorageKind() == ASTNodeKind; }
/// Return whether this location came from a SIL file.
bool isSILFile() const { return getStorageKind() == SILFileKind; }
/// Marks the location as coming from auto-generated body.
void markAutoGenerated() { KindData |= (1 << AutoGeneratedBit); }
@@ -235,37 +296,19 @@ public:
/// Check is this location is part of a function's implicit prologue.
bool isInPrologue() const { return KindData & (1 << IsInPrologue); }
void setHasSILFileSourceLoc() {
assert(!hasDebugLoc() &&
"SILFileSourceLoc and DebugLoc are mutually exclusive");
KindData |= (1 << HasSILFileSourceLoc);
}
bool hasSILFileSourceLoc() const {
return KindData & (1 << HasSILFileSourceLoc);
}
SourceLoc getSILFileSourceLoc() const {
assert(hasSILFileSourceLoc() && "no SILFileSourceLoc");
return SpecificLoc.SILFileSourceLoc;
}
/// Add an ASTNode to use as the location for debugging
/// purposes if this location is different from the location used
/// for diagnostics.
template <typename T>
void setDebugLoc(T *ASTNodeForDebugging) {
assert(!hasDebugLoc() && "DebugLoc already present");
assert(!hasSILFileSourceLoc() &&
"SILFileSourceLoc and DebugLoc are mutually exclusive");
KindData |= (1 << HasDebugLoc);
SpecificLoc.DebugLoc = ASTNodeForDebugging;
assert(isASTNode() && "not an AST location");
Loc.ASTNode.ForDebugger = ASTNodeForDebugging;
}
bool hasDebugLoc() const {
return KindData & (1 << HasDebugLoc);
return isASTNode() && !Loc.ASTNode.ForDebugger.isNull();
}
bool hasASTLocation() const { return !ASTNode.isNull(); }
/// Check if the corresponding source code location definitely points
/// to the start of the AST node.
bool alwaysPointsToStart() const { return KindData & (1 << PointsToStartBit);}
@@ -274,7 +317,12 @@ public:
/// to the end of the AST node.
bool alwaysPointsToEnd() const { return KindData & (1 << PointsToEndBit); }
LocationKind getKind() const { return (LocationKind)(KindData & BaseMask); }
LocationKind getKind() const {
return LocationKind(KindData & LocationKindMask);
}
StorageKind getStorageKind() const {
return StorageKind(KindData & StorageKindMask);
}
template <typename T>
bool is() const {
@@ -302,25 +350,28 @@ public:
/// If the current value is of the specified AST unit type T,
/// return it, otherwise return null.
template <typename T>
T *getAsASTNode() const { return getNodeAs<T>(ASTNode); }
template <typename T> T *getAsASTNode() const {
return isASTNode() ? getNodeAs<T>(Loc.ASTNode.Primary) : nullptr;
}
/// Returns true if the Location currently points to the AST node
/// matching type T.
template <typename T>
bool isASTNode() const { return isNode<T>(ASTNode); }
template <typename T> bool isASTNode() const {
return isASTNode() && isNode<T>(Loc.ASTNode.Primary);
}
/// Returns the primary value as the specified AST node type. If the
/// specified type is incorrect, asserts.
template <typename T>
T *castToASTNode() const { return castNodeTo<T>(ASTNode); }
template <typename T> T *castToASTNode() const {
assert(isASTNode());
return castNodeTo<T>(Loc.ASTNode.Primary);
}
/// If the DebugLoc is of the specified AST unit type T,
/// return it, otherwise return null.
template <typename T>
T *getDebugLocAsASTNode() const {
template <typename T> T *getDebugLocAsASTNode() const {
assert(hasDebugLoc() && "no debug location");
return getNodeAs<T>(SpecificLoc.DebugLoc);
return getNodeAs<T>(Loc.ASTNode.ForDebugger);
}
SourceLoc getDebugSourceLoc() const;
@@ -332,10 +383,11 @@ public:
return { getStartSourceLoc(), getEndSourceLoc() };
}
typedef struct {
unsigned Line = 0, Col = 0;
const char *Filename = nullptr;
} DebugLoc;
/// Fingerprint a DebugLoc for use in a DenseMap.
typedef std::pair<std::pair<unsigned, unsigned>, const void *> DebugLocKey;
struct DebugLocHash : public DebugLocKey {
DebugLocHash(DebugLoc L) : DebugLocKey({{L.Line, L.Col}, L.Filename}) {}
};
/// Extract the line, column, and filename.
static DebugLoc decode(SourceLoc Loc, const SourceManager &SM);
@@ -352,17 +404,21 @@ public:
/// Returns an opaque pointer value for the debug location that may
/// be used to unique debug locations.
const void *getOpaquePointerValue() const {
if (hasSILFileSourceLoc())
return getSILFileSourceLoc().getOpaquePointerValue();
return ASTNode.getOpaqueValue();
if (isSILFile())
return Loc.SILFileLoc.getOpaquePointerValue();
if (isASTNode())
return Loc.ASTNode.Primary.getOpaqueValue();
else
return 0;
}
unsigned getOpaqueKind() const { return KindData; }
inline bool operator==(const SILLocation& R) const {
return KindData == R.KindData &&
ASTNode.getOpaqueValue() == R.ASTNode.getOpaqueValue() &&
SpecificLoc.DebugLoc.getOpaqueValue() ==
R.SpecificLoc.DebugLoc.getOpaqueValue();
Loc.ASTNode.Primary.getOpaqueValue() ==
R.Loc.ASTNode.Primary.getOpaqueValue() &&
Loc.ASTNode.ForDebugger.getOpaqueValue() ==
R.Loc.ASTNode.ForDebugger.getOpaqueValue();
}
};
@@ -373,6 +429,7 @@ public:
RegularLocation(Expr *E) : SILLocation(E, RegularKind) {}
RegularLocation(Decl *D) : SILLocation(D, RegularKind) {}
RegularLocation(Pattern *P) : SILLocation(P, RegularKind) {}
RegularLocation(SourceLoc L) : SILLocation(L, RegularKind) {}
/// Returns a location representing the module.
static RegularLocation getModuleLocation() {
@@ -383,18 +440,15 @@ public:
/// If the current value is of the specified AST unit type T,
/// return it, otherwise return null.
template <typename T>
T *getAs() const { return getNodeAs<T>(ASTNode); }
template <typename T> T *getAs() const { return getNodeAs<T>(Loc.ASTNode); }
/// Returns true if the Location currently points to the AST node
/// matching type T.
template <typename T>
bool is() const { return isNode<T>(ASTNode); }
template <typename T> bool is() const { return isNode<T>(Loc.ASTNode); }
/// Returns the primary value as the specified AST node type. If the
/// specified type is incorrect, asserts.
template <typename T>
T *castTo() const { return castNodeTo<T>(ASTNode); }
template <typename T> T *castTo() const { return castNodeTo<T>(Loc.ASTNode); }
static RegularLocation getAutoGeneratedLocation() {
RegularLocation AL;
@@ -425,13 +479,11 @@ public:
ReturnStmt *get() {
return castToASTNode<ReturnStmt>();
}
private:
friend class SILLocation;
static bool isKind(const SILLocation& L) {
return L.getKind() == ReturnKind;
}
ReturnLocation() : SILLocation(ReturnKind) {}
};
/// Used on the instruction that was generated to represent an implicit
@@ -459,7 +511,7 @@ public:
L.isASTNode<ValueDecl>() ||
L.isASTNode<PatternBindingDecl>() ||
(L.isNull() && L.isInTopLevel()));
L.setKind(ImplicitReturnKind);
L.setLocationKind(ImplicitReturnKind);
return L;
}
@@ -492,8 +544,8 @@ public:
/// Constructs an inlined location when the call site is represented by a
/// SILFile location.
InlinedLocation(SourceLoc L) : SILLocation(InlinedKind) {
setHasSILFileSourceLoc();
SpecificLoc.SILFileSourceLoc = L;
setStorageKind(SILFileKind);
Loc.SILFileLoc = L;
}
static InlinedLocation getInlinedLocation(SILLocation L);
@@ -509,10 +561,7 @@ private:
InlinedLocation(Stmt *S, unsigned F) : SILLocation(S, InlinedKind, F) {}
InlinedLocation(Pattern *P, unsigned F) : SILLocation(P, InlinedKind, F) {}
InlinedLocation(Decl *D, unsigned F) : SILLocation(D, InlinedKind, F) {}
InlinedLocation(SourceLoc L, unsigned F) : SILLocation(InlinedKind, F) {
setHasSILFileSourceLoc();
SpecificLoc.SILFileSourceLoc = L;
}
InlinedLocation(SourceLoc L, unsigned F) : SILLocation(L, InlinedKind, F) {}
static InlinedLocation getModuleLocation(unsigned Flags) {
auto L = InlinedLocation();
@@ -539,10 +588,8 @@ public:
/// Constructs an inlined location when the call site is represented by a
/// SILFile location.
MandatoryInlinedLocation(SourceLoc L) : SILLocation(MandatoryInlinedKind) {
setHasSILFileSourceLoc();
SpecificLoc.SILFileSourceLoc = L;
}
MandatoryInlinedLocation(SourceLoc L)
: SILLocation(L, MandatoryInlinedKind) {}
static MandatoryInlinedLocation getMandatoryInlinedLocation(SILLocation L);
@@ -558,23 +605,16 @@ private:
return L.getKind() == MandatoryInlinedKind;
}
MandatoryInlinedLocation() : SILLocation(MandatoryInlinedKind) {}
MandatoryInlinedLocation(Expr *E,
unsigned F) : SILLocation(E, MandatoryInlinedKind,
F) {}
MandatoryInlinedLocation(Stmt *S,
unsigned F) : SILLocation(S, MandatoryInlinedKind,
F) {}
MandatoryInlinedLocation(Pattern *P,
unsigned F) : SILLocation(P, MandatoryInlinedKind,
F) {}
MandatoryInlinedLocation(Decl *D,
unsigned F) : SILLocation(D, MandatoryInlinedKind,
F) {}
MandatoryInlinedLocation(SourceLoc L,
unsigned F) : SILLocation(MandatoryInlinedKind, F) {
setHasSILFileSourceLoc();
SpecificLoc.SILFileSourceLoc = L;
}
MandatoryInlinedLocation(Expr *E, unsigned F)
: SILLocation(E, MandatoryInlinedKind, F) {}
MandatoryInlinedLocation(Stmt *S, unsigned F)
: SILLocation(S, MandatoryInlinedKind, F) {}
MandatoryInlinedLocation(Pattern *P, unsigned F)
: SILLocation(P, MandatoryInlinedKind, F) {}
MandatoryInlinedLocation(Decl *D, unsigned F)
: SILLocation(D, MandatoryInlinedKind, F) {}
MandatoryInlinedLocation(SourceLoc L, unsigned F)
: SILLocation(L, MandatoryInlinedKind, F) {}
};
/// Used on the instruction performing auto-generated cleanup such as
@@ -627,7 +667,6 @@ private:
class ArtificialUnreachableLocation : public SILLocation {
public:
ArtificialUnreachableLocation() : SILLocation(ArtificialUnreachableKind) {}
private:
friend class SILLocation;
static bool isKind(const SILLocation& L) {
@@ -635,27 +674,6 @@ private:
}
};
/// Used to represent locations coming from a parsed SIL file.
///
/// Allowed on any SILInstruction.
class SILFileLocation : public SILLocation {
public:
SILFileLocation(SourceLoc L) : SILLocation(SILFileKind) {
setHasSILFileSourceLoc();
SpecificLoc.SILFileSourceLoc = L;
}
private:
friend class SILLocation;
static bool isKind(const SILLocation& L) {
return L.getKind() == SILFileKind;
}
SILFileLocation() : SILLocation(SILFileKind) {
setHasSILFileSourceLoc();
SpecificLoc.SILFileSourceLoc = SourceLoc();
}
};
} // end swift namespace

View File

@@ -348,7 +348,7 @@ void IRGenDebugInfo::setCurrentLoc(IRBuilder &Builder, const SILDebugScope *DS,
//
// The actual closure has a closure expression as scope.
if (Loc && isAbstractClosure(*Loc) && DS && !isAbstractClosure(DS->Loc)
&& Loc->getKind() != SILLocation::ImplicitReturnKind)
&& !Loc->is<ImplicitReturnLocation>())
return;
if (L.Line == 0 && DS == LastScope) {
@@ -660,7 +660,7 @@ llvm::DISubprogram *IRGenDebugInfo::emitFunction(
StringRef Name;
if (DS) {
if (DS->Loc.getKind() == SILLocation::SILFileKind)
if (DS->Loc.isSILFile())
Name = SILFn->getName();
else
Name = getName(DS->Loc);

View File

@@ -1547,7 +1547,7 @@ void IRGenSILFunction::visitSILBasicBlock(SILBasicBlock *BB) {
SILLocation ILoc = I.getLoc();
auto DS = I.getDebugScope();
// Handle cleanup locations.
if (ILoc.getKind() == SILLocation::CleanupKind) {
if (ILoc.is<CleanupLocation>()) {
// Cleanup locations point to the decl of the value that is
// being destroyed (for diagnostic generation). As far as
// the linetable is concerned, cleanups at the end of a
@@ -1559,7 +1559,7 @@ void IRGenSILFunction::visitSILBasicBlock(SILBasicBlock *BB) {
// this basic block.
auto It = InsnIter;
do ++It; while (It != BB->end() &&
It->getLoc().getKind() == SILLocation::CleanupKind);
It->getLoc().is<CleanupLocation>());
// We are still in the middle of a basic block?
if (It != BB->end() && !isa<TermInst>(It))
KeepCurrentLocation = true;

View File

@@ -366,7 +366,7 @@ SILFunction *SILParser::getGlobalNameForDefinition(Identifier Name,
P.diagnose(Loc, diag::sil_value_use_type_mismatch, Name.str(),
Fn->getLoweredFunctionType(), Ty);
P.diagnose(It->second.second, diag::sil_prior_reference);
auto loc = SILFileLocation(Loc);
auto loc = RegularLocation(Loc);
Fn =
SILMod.getOrCreateFunction(SILLinkage::Private, "", Ty, nullptr, loc,
IsNotBare, IsNotTransparent, IsNotFragile);
@@ -383,7 +383,7 @@ SILFunction *SILParser::getGlobalNameForDefinition(Identifier Name,
return Fn;
}
auto loc = SILFileLocation(Loc);
auto loc = RegularLocation(Loc);
// If we don't have a forward reference, make sure the function hasn't been
// defined already.
if (SILMod.lookUpFunction(Name.str()) != nullptr) {
@@ -410,7 +410,7 @@ SILFunction *SILParser::getGlobalNameForDefinition(Identifier Name,
SILFunction *SILParser::getGlobalNameForReference(Identifier Name,
CanSILFunctionType Ty,
SourceLoc Loc) {
auto loc = SILFileLocation(Loc);
auto loc = RegularLocation(Loc);
// Check to see if we have a function by this name already.
if (SILFunction *FnRef = SILMod.lookUpFunction(Name.str())) {
@@ -1042,7 +1042,7 @@ bool SILParser::parseTypedValueRef(SILValue &Result, SourceLoc &Loc,
parseSILType(Ty))
return true;
Result = getLocalValue(Name, Ty, SILFileLocation(Loc), B);
Result = getLocalValue(Name, Ty, RegularLocation(Loc), B);
return false;
}
@@ -1443,7 +1443,7 @@ bool SILParser::parseSILInstruction(SILBasicBlock *BB) {
SmallVector<SILValue, 4> OpList;
SILValue Val;
SILLocation InstLoc = SILFileLocation(OpcodeLoc);
SILLocation InstLoc = RegularLocation(OpcodeLoc);
auto parseCastConsumptionKind = [&](Identifier name, SourceLoc loc,
CastConsumptionKind &out) -> bool {
@@ -2337,7 +2337,7 @@ bool SILParser::parseSILInstruction(SILBasicBlock *BB) {
Type EltTy = TT->getElement(TypeElts.size()).getType();
if (parseValueRef(Val,
SILType::getPrimitiveObjectType(EltTy->getCanonicalType()),
SILFileLocation(P.Tok.getLoc()), B))
RegularLocation(P.Tok.getLoc()), B))
return true;
OpList.push_back(Val);
TypeElts.push_back(Val->getType().getSwiftRValueType());
@@ -2930,7 +2930,7 @@ bool SILParser::parseSILInstruction(SILBasicBlock *BB) {
// Parse 'case' value-ref ':' sil-identifier.
if (P.consumeIf(tok::kw_case)) {
if (parseValueRef(CaseVal, Val->getType(),
SILFileLocation(P.Tok.getLoc()), B)) {
RegularLocation(P.Tok.getLoc()), B)) {
// TODO: Issue a proper error message here
P.diagnose(P.Tok, diag::expected_tok_in_sil_instr, "reference to a value");
return true;
@@ -3618,7 +3618,7 @@ bool Parser::parseSILGlobal() {
auto *GV = SILGlobalVariable::create(*SIL->M, GlobalLinkage.getValue(),
(IsFragile_t)isFragile,
GlobalName.str(),GlobalType,
SILFileLocation(NameLoc));
RegularLocation(NameLoc));
GV->setLet(isLet);
// Parse static initializer if exists.

View File

@@ -27,7 +27,7 @@ void swift::printSILLocationDescription(llvm::raw_ostream &out,
ASTContext &Context) {
if (loc.isNull()) {
out << "<<invalid location>>";
} else if (!loc.hasASTLocation()) {
} else if (loc.isSILFile()) {
printSourceLocDescription(out, loc.getSourceLoc(), Context);
} else if (auto decl = loc.getAsASTNode<Decl>()) {
printDeclDescription(out, decl, Context);
@@ -35,8 +35,7 @@ void swift::printSILLocationDescription(llvm::raw_ostream &out,
printExprDescription(out, expr, Context);
} else if (auto stmt = loc.getAsASTNode<Stmt>()) {
printStmtDescription(out, stmt, Context);
} else {
auto pattern = loc.castToASTNode<Pattern>();
} else if (auto pattern = loc.castToASTNode<Pattern>()) {
printPatternDescription(out, pattern, Context);
}
}

View File

@@ -22,10 +22,10 @@ using namespace swift;
SourceLoc SILLocation::getSourceLoc() const {
if (hasSILFileSourceLoc())
return getSILFileSourceLoc();
if (isSILFile())
return Loc.SILFileLoc;
return getSourceLoc(ASTNode);
return getSourceLoc(Loc.ASTNode.Primary);
}
SourceLoc SILLocation::getSourceLoc(ASTNodeTy N) const {
@@ -34,12 +34,12 @@ SourceLoc SILLocation::getSourceLoc(ASTNodeTy N) const {
if (alwaysPointsToStart() ||
alwaysPointsToEnd() ||
getKind() == CleanupKind ||
getKind() == ImplicitReturnKind)
is<CleanupLocation>() ||
is<ImplicitReturnLocation>())
return getEndSourceLoc(N);
// Use the start location for the ReturnKind.
if (getKind() == ReturnKind)
if (is<ReturnLocation>())
return getStartSourceLoc(N);
if (auto *decl = N.dyn_cast<Decl*>())
@@ -54,13 +54,13 @@ SourceLoc SILLocation::getSourceLoc(ASTNodeTy N) const {
}
SourceLoc SILLocation::getDebugSourceLoc() const {
if (hasSILFileSourceLoc())
return getSILFileSourceLoc();
if (isSILFile())
return Loc.SILFileLoc;
if (isAutoGenerated())
return SourceLoc();
if (auto *expr = ASTNode.dyn_cast<Expr*>()) {
if (auto *expr = Loc.ASTNode.Primary.dyn_cast<Expr*>()) {
if (isa<CallExpr>(expr))
return expr->getEndLoc();
// Code that has an autoclosure as location should not show up in
@@ -73,19 +73,18 @@ SourceLoc SILLocation::getDebugSourceLoc() const {
return SourceLoc();
}
if (!hasDebugLoc())
return getSourceLoc(ASTNode);
if (Loc.ASTNode.ForDebugger)
return getSourceLoc(Loc.ASTNode.ForDebugger);
assert(!SpecificLoc.DebugLoc.isNull() && "empty debug location");
return getSourceLoc(SpecificLoc.DebugLoc);
return getSourceLoc(Loc.ASTNode.Primary);
}
SourceLoc SILLocation::getStartSourceLoc() const {
if (isAutoGenerated())
return SourceLoc();
if (ASTNode.isNull())
return getSILFileSourceLoc();
return getStartSourceLoc(ASTNode);
if (isSILFile())
return Loc.SILFileLoc;
return getStartSourceLoc(Loc.ASTNode.Primary);
}
SourceLoc SILLocation::getStartSourceLoc(ASTNodeTy N) const {
@@ -103,9 +102,9 @@ SourceLoc SILLocation::getStartSourceLoc(ASTNodeTy N) const {
SourceLoc SILLocation::getEndSourceLoc() const {
if (isAutoGenerated())
return SourceLoc();
if (ASTNode.isNull())
return getSILFileSourceLoc();
return getEndSourceLoc(ASTNode);
if (isSILFile())
return Loc.SILFileLoc;
return getEndSourceLoc(Loc.ASTNode.Primary);
}
SourceLoc SILLocation::getEndSourceLoc(ASTNodeTy N) const {
@@ -131,13 +130,13 @@ SILLocation::DebugLoc SILLocation::decode(SourceLoc Loc,
}
void SILLocation::dump(const SourceManager &SM) const {
if (auto D = ASTNode.dyn_cast<Decl *>())
if (auto D = getAsASTNode<Decl>())
llvm::errs() << Decl::getKindName(D->getKind()) << "Decl @ ";
if (auto E = ASTNode.dyn_cast<Expr *>())
if (auto E = getAsASTNode<Expr>())
llvm::errs() << Expr::getKindName(E->getKind()) << "Expr @ ";
if (auto S = ASTNode.dyn_cast<Stmt *>())
if (auto S = getAsASTNode<Stmt>())
llvm::errs() << Stmt::getKindName(S->getKind()) << "Stmt @ ";
if (auto P = ASTNode.dyn_cast<Pattern *>())
if (auto P = getAsASTNode<Pattern>())
llvm::errs() << Pattern::getKindName(P->getKind()) << "Pattern @ ";
print(llvm::errs(), SM);
@@ -147,7 +146,7 @@ void SILLocation::dump(const SourceManager &SM) const {
if (alwaysPointsToEnd()) llvm::errs() << ":end";
if (isInTopLevel()) llvm::errs() << ":toplevel";
if (isInPrologue()) llvm::errs() << ":prologue";
if (hasSILFileSourceLoc()) llvm::errs() << ":sil";
if (isSILFile()) llvm::errs() << ":sil";
if (hasDebugLoc()) {
llvm::errs() << ":debug[";
getDebugSourceLoc().print(llvm::errs(), SM);
@@ -171,8 +170,8 @@ InlinedLocation InlinedLocation::getInlinedLocation(SILLocation L) {
if (Decl *D = L.getAsASTNode<Decl>())
return InlinedLocation(D, L.getSpecialFlags());
if (L.hasSILFileSourceLoc())
return InlinedLocation(L.getSILFileSourceLoc(), L.getSpecialFlags());
if (L.isSILFile())
return InlinedLocation(L.Loc.SILFileLoc, L.getSpecialFlags());
if (L.isInTopLevel())
return InlinedLocation::getModuleLocation(L.getSpecialFlags());
@@ -196,9 +195,8 @@ MandatoryInlinedLocation::getMandatoryInlinedLocation(SILLocation L) {
if (Decl *D = L.getAsASTNode<Decl>())
return MandatoryInlinedLocation(D, L.getSpecialFlags());
if (L.hasSILFileSourceLoc())
return MandatoryInlinedLocation(L.getSILFileSourceLoc(),
L.getSpecialFlags());
if (L.isSILFile())
return MandatoryInlinedLocation(L.Loc.SILFileLoc, L.getSpecialFlags());
if (L.isInTopLevel())
return MandatoryInlinedLocation::getModuleLocation(L.getSpecialFlags());
@@ -217,7 +215,7 @@ CleanupLocation CleanupLocation::get(SILLocation L) {
return CleanupLocation(D, L.getSpecialFlags());
if (L.isNull())
return CleanupLocation();
if (L.getAs<SILFileLocation>())
if (L.isSILFile())
return CleanupLocation();
llvm_unreachable("Cannot construct Cleanup loc from the "
"given location.");

View File

@@ -597,10 +597,9 @@ public:
case SILLocation::ArtificialUnreachableKind:
*this << ":art_unreach";
break;
case SILLocation::SILFileKind:
*this << ":sil";
break;
}
if (L.isSILFile())
*this << ":sil";
if (L.isAutoGenerated())
*this << ":auto_gen";
if (L.isInPrologue())

View File

@@ -531,9 +531,8 @@ public:
SILLocation::LocationKind LocKind = L.getKind();
ValueKind InstKind = I->getKind();
// Regular locations and SIL file locations are allowed on all instructions.
if (LocKind == SILLocation::RegularKind ||
LocKind == SILLocation::SILFileKind)
// Regular locations are allowed on all instructions.
if (LocKind == SILLocation::RegularKind)
return;
#if 0

View File

@@ -51,7 +51,7 @@ llvm::cl::opt<bool> EnableLoopARC("enable-loop-arc", llvm::cl::init(true));
static SILInstruction *createIncrement(SILValue Ptr, SILInstruction *InsertPt) {
// Set up the builder we use to insert at our insertion point.
SILBuilder B(InsertPt);
auto Loc = SILFileLocation(SourceLoc());
auto Loc = RegularLocation(SourceLoc());
// If Ptr is refcounted itself, create the strong_retain and
// return.
@@ -68,7 +68,7 @@ static SILInstruction *createIncrement(SILValue Ptr, SILInstruction *InsertPt) {
static SILInstruction *createDecrement(SILValue Ptr, SILInstruction *InsertPt) {
// Setup the builder we will use to insert at our insertion point.
SILBuilder B(InsertPt);
auto Loc = SILFileLocation(SourceLoc());
auto Loc = RegularLocation(SourceLoc());
// If Ptr has reference semantics itself, create a strong_release.
if (Ptr->getType().isReferenceCounted(B.getModule()))

View File

@@ -1031,7 +1031,7 @@ static SILInstruction *isSuperInitUse(UpcastInst *Inst) {
// If we're reading a .sil file, treat a call to "superinit" as a
// super.init call as a hack to allow us to write testcases.
auto *AI = dyn_cast<ApplyInst>(inst);
if (AI && inst->getLoc().is<SILFileLocation>())
if (AI && inst->getLoc().isSILFile())
if (auto *Fn = AI->getCalleeFunction())
if (Fn->getName() == "superinit")
return inst;
@@ -1070,7 +1070,7 @@ static SILInstruction *isSuperInitUse(UpcastInst *Inst) {
static bool isSelfInitUse(SILInstruction *I) {
// If we're reading a .sil file, treat a call to "selfinit" as a
// self.init call as a hack to allow us to write testcases.
if (I->getLoc().is<SILFileLocation>()) {
if (I->getLoc().isSILFile()) {
if (auto *AI = dyn_cast<ApplyInst>(I))
if (auto *Fn = AI->getCalleeFunction())
if (Fn->getName().startswith("selfinit"))

View File

@@ -75,7 +75,7 @@ static void diagnoseUnreachable(const SILInstruction *I,
// transparently inlined. We should have already emitted these
// diagnostics when we process the callee function prior to
// inlining it.
if (!L.hasASTLocation() || L.is<MandatoryInlinedLocation>())
if (!L || L.is<MandatoryInlinedLocation>())
return;
// The most common case of getting an unreachable instruction is a

View File

@@ -183,7 +183,7 @@ static void analyzeUseOfInOut(Operand *UI, StackSlotState &state) {
// We only look at autogenerated copy_addr's. We don't want to muck with
// user variables, as in:
// func f(inout a : Int) { var b = a }
if (!CAI->getLoc().isAutoGenerated() && !CAI->getLoc().is<SILFileLocation>())
if (!CAI->getLoc().isAutoGenerated() && !CAI->getLoc().isSILFile())
return;
// Get a stack slot, looking through mark_uninitialized if necessary.

View File

@@ -34,8 +34,8 @@ static SILBasicBlock *createInitialPreheader(SILBasicBlock *Header) {
}
// Create the branch to the header.
SILBuilder(Preheader)
.createBranch(SILFileLocation(SourceLoc()), Header, Args);
SILBuilder(Preheader).createBranch(RegularLocation(SourceLoc()), Header,
Args);
return Preheader;
}

View File

@@ -282,7 +282,7 @@ static SILFunction *createBogusSILFunction(SILModule &M,
SourceLoc loc;
return M.getOrCreateFunction(
SILLinkage::Private, name, type.castTo<SILFunctionType>(), nullptr,
SILFileLocation(loc), IsNotBare, IsNotTransparent, IsNotFragile,
RegularLocation(loc), IsNotBare, IsNotTransparent, IsNotFragile,
IsNotThunk, SILFunction::NotRelevant);
}
@@ -402,7 +402,7 @@ SILFunction *SILDeserializer::readSILFunction(DeclID FID,
auto fn = existingFn;
// TODO: use the correct SILLocation from module.
SILLocation loc = SILFileLocation(SourceLoc());
SILLocation loc = RegularLocation(SourceLoc());
// If we have an existing function, verify that the types match up.
if (fn) {
@@ -624,7 +624,7 @@ bool SILDeserializer::readSILInstruction(SILFunction *Fn, SILBasicBlock *BB,
ModuleID OwningModuleID;
SourceLoc SLoc;
ArrayRef<uint64_t> ListOfValues;
SILLocation Loc = SILFileLocation(SLoc);
SILLocation Loc = RegularLocation(SLoc);
switch (RecordKind) {
default: