Files
swift-mirror/include/swift/Basic/SourceManager.h
Dmitri Hrybenko ecd798b9fd Comment parsing: attaching comments to declarations
We can attach comments to declarations.  Right now we only support comments
that precede the declarations (trailing comments will be supported later).

The implementation approach is different from one we have in Clang.  In Swift
the Lexer attaches the comments to the next token, and parser checks if
comments are present on the first token of the declaration.  This is much
cleaner, and faster than Clang's approach (where we perform a binary search on
source locations and do ad-hoc fixups afterwards).

The comment <-> decl correspondence is modeled as "virtual" attributes that can
not be spelled in the source.  These attributes are not serialized at the
moment -- this will be implemented later.


Swift SVN r14031
2014-02-18 09:04:37 +00:00

138 lines
4.5 KiB
C++

//===--- SourceManager.h - Manager for Source Buffers -----------*- C++ -*-===//
//
// This source file is part of the Swift.org open source project
//
// Copyright (c) 2014 - 2015 Apple Inc. and the Swift project authors
// Licensed under Apache License v2.0 with Runtime Library Exception
//
// See http://swift.org/LICENSE.txt for license information
// See http://swift.org/CONTRIBUTORS.txt for the list of Swift project authors
//
//===----------------------------------------------------------------------===//
#ifndef SWIFT_SOURCEMANAGER_H
#define SWIFT_SOURCEMANAGER_H
#include "swift/Basic/SourceLoc.h"
#include "swift/Basic/Optional.h"
#include "llvm/ADT/StringMap.h"
#include "llvm/Support/SourceMgr.h"
namespace swift {
/// \brief This class manages and owns source buffers.
class SourceManager {
llvm::SourceMgr LLVMSourceMgr;
unsigned CodeCompletionBufferID = ~0U;
unsigned CodeCompletionOffset;
/// \brief The buffer ID where a hashbang line #! is allowed.
unsigned HashbangBufferID = ~0U;
/// Associates buffer identifiers to buffer IDs.
llvm::StringMap<unsigned> BufIdentIDMap;
public:
SourceManager() {}
llvm::SourceMgr *operator->() { return &LLVMSourceMgr; }
const llvm::SourceMgr *operator->() const { return &LLVMSourceMgr; }
const llvm::SourceMgr &getLLVMSourceMgr() const {
return LLVMSourceMgr;
}
void setCodeCompletionPoint(unsigned BufferID, unsigned Offset) {
assert(BufferID != ~0U && "Buffer should be valid");
CodeCompletionBufferID = BufferID;
CodeCompletionOffset = Offset;
}
unsigned getCodeCompletionBufferID() const {
return CodeCompletionBufferID;
}
unsigned getCodeCompletionOffset() const {
return CodeCompletionOffset;
}
SourceLoc getCodeCompletionLoc() const;
void setHashbangBufferID(unsigned BufferID) {
assert(HashbangBufferID == ~0U && "Hashbang buffer ID already set");
HashbangBufferID = BufferID;
}
unsigned getHashbangBufferID() const {
return HashbangBufferID;
}
/// Returns true if \c LHS is before \c RHS in the source buffer.
bool isBeforeInBuffer(SourceLoc LHS, SourceLoc RHS) const {
return LHS.Value.getPointer() < RHS.Value.getPointer();
}
/// Returns true if range \c R contains the location \c Loc. The location
/// \c Loc should point at the beginning of the token.
bool rangeContainsTokenLoc(SourceRange R, SourceLoc Loc) const {
return Loc == R.Start || Loc == R.End ||
(isBeforeInBuffer(R.Start, Loc) && isBeforeInBuffer(Loc, R.End));
}
/// Returns true if range \c Enclosing contains the range \c Inner.
bool rangeContains(SourceRange Enclosing, SourceRange Inner) const {
return rangeContainsTokenLoc(Enclosing, Inner.Start) &&
rangeContainsTokenLoc(Enclosing, Inner.End);
}
/// Returns the buffer ID for the specified *valid* location.
///
/// Because a valid source location always corresponds to a source buffer,
/// this routine always returns a valid buffer ID.
unsigned findBufferContainingLoc(SourceLoc Loc) const {
assert(Loc.isValid());
int BufferID = LLVMSourceMgr.FindBufferContainingLoc(Loc.Value);
assert(BufferID != -1);
return unsigned(BufferID);
}
size_t addNewSourceBuffer(llvm::MemoryBuffer *Buffer);
/// Returns a buffer ID for a previously added buffer with the given
/// buffer identifier, or Nothing if there is no such buffer.
Optional<unsigned> getIDForBufferIdentifier(StringRef BufIdentifier);
/// \brief Returns the SourceLoc for the beginning of the specified buffer
/// (at offset zero).
///
/// Note that the resulting location might not point at the first token: it
/// might point at whitespace or comment.
SourceLoc getLocForBufferStart(unsigned BufferID) const;
/// \brief Returns the offset in bytes for the given source location.
unsigned getLocOffsetInBuffer(SourceLoc Loc, unsigned BufferID) const;
/// \brief Returns the distance in bytes between the given source locations.
unsigned getByteDistance(SourceLoc Start, SourceLoc End) const;
/// Returns the SourceLoc for the byte offset in the specified buffer.
SourceLoc getLocForOffset(unsigned BufferID, unsigned Offset) const {
return getLocForBufferStart(BufferID).getAdvancedLoc(Offset);
}
std::pair<unsigned, unsigned> getLineAndColumn(SourceLoc Loc,
int BufferID = -1) const {
assert(Loc.isValid());
return LLVMSourceMgr.getLineAndColumn(Loc.Value, BufferID);
}
StringRef extractText(CharSourceRange Range) const;
};
} // namespace swift
#endif // LLVM_SWIFT_SOURCEMANAGER_H