mirror of
https://github.com/apple/swift.git
synced 2025-12-14 20:36:38 +01:00
Implement SerializedModuleLoader::addASTSection() to parse AST sections as
created by IrGen/SwiftASTStreamerPass. Swift SVN r7851
This commit is contained in:
@@ -16,11 +16,13 @@
|
||||
#include "swift/AST/AST.h"
|
||||
#include "swift/AST/Component.h"
|
||||
#include "swift/AST/Diagnostics.h"
|
||||
#include "swift/Basic/Dwarf.h"
|
||||
#include "swift/Basic/STLExtras.h"
|
||||
#include "swift/Basic/SourceManager.h"
|
||||
#include "llvm/ADT/SmallString.h"
|
||||
#include "llvm/Support/MemoryBuffer.h"
|
||||
#include "llvm/Support/Path.h"
|
||||
#include "llvm/Support/Debug.h"
|
||||
#include "llvm/Support/system_error.h"
|
||||
|
||||
using namespace swift;
|
||||
@@ -80,6 +82,66 @@ static llvm::error_code findModule(ASTContext &ctx, AccessPathElem moduleID,
|
||||
}
|
||||
|
||||
|
||||
bool SerializedModuleLoader::
|
||||
addASTSection(std::unique_ptr<llvm::MemoryBuffer> MemoryBuffer,
|
||||
SmallVectorImpl<std::string> &foundModules) {
|
||||
struct apple_ast_hdr {
|
||||
uint32_t version;
|
||||
uint32_t nmods;
|
||||
};
|
||||
|
||||
struct module_header {
|
||||
uint64_t bitstream_ofs;
|
||||
uint64_t bitstream_size;
|
||||
uint64_t name_ofs;
|
||||
uint32_t language;
|
||||
uint32_t flags;
|
||||
};
|
||||
|
||||
if (MemoryBuffer->getBufferSize() < sizeof(struct apple_ast_hdr)
|
||||
+ sizeof(struct module_header)) {
|
||||
llvm::dbgs() << "__apple_ast section is too small.\n";
|
||||
return false;
|
||||
}
|
||||
|
||||
size_t size = MemoryBuffer->getBufferSize();
|
||||
const char *data = MemoryBuffer->getBufferStart();
|
||||
auto apple_ast_hdr = reinterpret_cast<const struct apple_ast_hdr *>(data);
|
||||
if (apple_ast_hdr->version != 1) {
|
||||
llvm::dbgs() << "Unsupported __apple_ast section version.\n";
|
||||
return false;
|
||||
}
|
||||
|
||||
// Iterate over all AST modules.
|
||||
for (uint32_t i = 0; i < apple_ast_hdr->nmods; ++i) {
|
||||
auto mh = reinterpret_cast<const struct module_header *>
|
||||
(data+sizeof(apple_ast_hdr));
|
||||
|
||||
if (mh->language != dwarf::DW_LANG_Swift)
|
||||
continue;
|
||||
|
||||
// Get the access path.
|
||||
if (mh->name_ofs + 4 > size) return false;
|
||||
auto nchars = *reinterpret_cast<const uint32_t *>(data + mh->name_ofs);
|
||||
if (mh->name_ofs+sizeof(nchars) > size) return false;
|
||||
assert(nchars < (2 << 10) && "path failed sanity check");
|
||||
llvm::StringRef AccessPath(data+mh->name_ofs+sizeof(nchars), nchars);
|
||||
|
||||
// loadModule() wants to take ownership of the input memory buffer.
|
||||
// Copy the bitstream into a new memory buffer.
|
||||
if (mh->bitstream_ofs + mh->bitstream_size > size) return false;
|
||||
auto mem = llvm::StringRef(data+mh->bitstream_ofs, mh->bitstream_size);
|
||||
auto bitstream = llvm::MemoryBuffer::getMemBufferCopy(mem, AccessPath);
|
||||
|
||||
// Register the memory buffer.
|
||||
registerMemoryBuffer(AccessPath,
|
||||
std::unique_ptr<llvm::MemoryBuffer>(bitstream));
|
||||
foundModules.push_back(AccessPath);
|
||||
}
|
||||
return true;
|
||||
}
|
||||
|
||||
|
||||
Module *SerializedModuleLoader::loadModule(SourceLoc importLoc,
|
||||
Module::AccessPathTy path) {
|
||||
// FIXME: Swift submodules?
|
||||
@@ -89,18 +151,18 @@ Module *SerializedModuleLoader::loadModule(SourceLoc importLoc,
|
||||
auto moduleID = path[0];
|
||||
|
||||
llvm::OwningPtr<llvm::MemoryBuffer> inputFile;
|
||||
// First see if we find it in the registered bitstreams.
|
||||
// First see if we find it in the registered memory buffers.
|
||||
if (!MemoryBuffers.empty()) {
|
||||
// FIXME: Right now this works only with fully-qualified absolute
|
||||
// pathnames, which is incidentally what LLDB uses. Fix this to
|
||||
// support suffix matching and a search path.
|
||||
// FIXME: Right now this works only with access paths of length 1.
|
||||
// Once submodules are designed, this needs to support suffix
|
||||
// matching and a search path.
|
||||
llvm::SmallString<256> spath;
|
||||
for (auto el : path)
|
||||
llvm::sys::path::append(spath, el.first.str());
|
||||
|
||||
auto bs = MemoryBuffers.find(spath.str());
|
||||
if (bs != MemoryBuffers.end())
|
||||
inputFile.reset(bs->second.take());
|
||||
inputFile.reset(bs->second.release());
|
||||
}
|
||||
|
||||
// Otherwise look on disk.
|
||||
@@ -236,7 +298,7 @@ SerializedModuleLoader::lookupVisibleDecls(const Module *module,
|
||||
ModuleFile *moduleFile = cast<SerializedModule>(module)->File;
|
||||
if (!moduleFile)
|
||||
return;
|
||||
|
||||
|
||||
moduleFile->lookupVisibleDecls(accessPath, consumer, lookupKind);
|
||||
}
|
||||
|
||||
|
||||
Reference in New Issue
Block a user