//===----------------------------------------------------------------------===//
#include "ArchiveInternals.h"
+#include "llvm/ADT/SmallPtrSet.h"
#include "llvm/Bitcode/ReaderWriter.h"
#include "llvm/Support/MemoryBuffer.h"
#include "llvm/Module.h"
+#include <cstdio>
#include <cstdlib>
#include <memory>
using namespace llvm;
}
// Cast archive member header
- ArchiveMemberHeader* Hdr = (ArchiveMemberHeader*)At;
+ const ArchiveMemberHeader* Hdr = (const ArchiveMemberHeader*)At;
At += sizeof(ArchiveMemberHeader);
- // Extract the size and determine if the file is
- // compressed or not (negative length).
int flags = 0;
int MemberSize = atoi(Hdr->size);
- if (MemberSize < 0) {
- flags |= ArchiveMember::CompressedFlag;
- MemberSize = -MemberSize;
- }
+ assert(MemberSize >= 0);
// Check the size of the member for sanity
if (At + MemberSize > End) {
if (isdigit(Hdr->name[3])) {
unsigned len = atoi(&Hdr->name[3]);
const char *nulp = (const char *)memchr(At, '\0', len);
- pathname.assign(At, nulp != 0 ? nulp - At : len);
+ pathname.assign(At, nulp != 0 ? (uintptr_t)(nulp - At) : len);
At += len;
MemberSize -= len;
flags |= ArchiveMember::HasLongFilenameFlag;
/* FALL THROUGH */
default:
- char* slash = (char*) memchr(Hdr->name, '/', 16);
+ const char* slash = (const char*) memchr(Hdr->name, '/', 16);
if (slash == 0)
slash = Hdr->name + 16;
pathname.assign(Hdr->name, slash - Hdr->name);
std::string FullMemberName = archPath.str() +
"(" + I->getPath().str() + ")";
MemoryBuffer *Buffer =
- MemoryBuffer::getNewMemBuffer(I->getSize(), FullMemberName.c_str());
- memcpy((char*)Buffer->getBufferStart(), I->getData(), I->getSize());
+ MemoryBuffer::getMemBufferCopy(StringRef(I->getData(), I->getSize()),
+ FullMemberName.c_str());
Module *M = ParseBitcodeFile(Buffer, Context, ErrMessage);
delete Buffer;
// Now, load the bitcode module to get the Module.
std::string FullMemberName = archPath.str() + "(" +
mbr->getPath().str() + ")";
- MemoryBuffer *Buffer =MemoryBuffer::getNewMemBuffer(mbr->getSize(),
- FullMemberName.c_str());
- memcpy((char*)Buffer->getBufferStart(), mbr->getData(), mbr->getSize());
+ MemoryBuffer *Buffer =
+ MemoryBuffer::getMemBufferCopy(StringRef(mbr->getData(), mbr->getSize()),
+ FullMemberName.c_str());
Module *m = getLazyBitcodeModule(Buffer, Context, ErrMsg);
if (!m)
// Modules that define those symbols.
bool
Archive::findModulesDefiningSymbols(std::set<std::string>& symbols,
- std::set<Module*>& result,
+ SmallVectorImpl<Module*>& result,
std::string* error) {
if (!mapfile || !base) {
if (error)
std::string FullMemberName = archPath.str() + "(" +
mbr->getPath().str() + ")";
Module* M =
- GetBitcodeSymbols((const unsigned char*)At, mbr->getSize(),
- FullMemberName, Context, symbols, error);
+ GetBitcodeSymbols(At, mbr->getSize(), FullMemberName, Context,
+ symbols, error);
if (M) {
// Insert the module's symbols into the symbol table
// At this point we have a valid symbol table (one way or another) so we
// just use it to quickly find the symbols requested.
+ SmallPtrSet<Module*, 16> Added;
for (std::set<std::string>::iterator I=symbols.begin(),
- E=symbols.end(); I != E;) {
+ Next = I,
+ E=symbols.end(); I != E; I = Next) {
+ // Increment Next before we invalidate it.
+ ++Next;
+
// See if this symbol exists
Module* m = findModuleDefiningSymbol(*I,error);
- if (m) {
- // The symbol exists, insert the Module into our result, duplicates will
- // be ignored.
- result.insert(m);
-
- // Remove the symbol now that its been resolved, being careful to
- // post-increment the iterator.
- symbols.erase(I++);
- } else {
- ++I;
- }
+ if (!m)
+ continue;
+ bool NewMember = Added.insert(m);
+ if (!NewMember)
+ continue;
+
+ // The symbol exists, insert the Module into our result.
+ result.push_back(m);
+
+ // Remove the symbol now that its been resolved.
+ symbols.erase(I);
}
return true;
}
archPath.str() + "(" + I->getPath().str() + ")";
MemoryBuffer *Buffer =
- MemoryBuffer::getNewMemBuffer(I->getSize(), FullMemberName.c_str());
- memcpy((char*)Buffer->getBufferStart(), I->getData(), I->getSize());
+ MemoryBuffer::getMemBufferCopy(StringRef(I->getData(), I->getSize()),
+ FullMemberName.c_str());
Module *M = ParseBitcodeFile(Buffer, Context);
delete Buffer;
if (!M)