parent
4ba81b2ee4
commit
ee1afa3082
|
@ -250,7 +250,10 @@ namespace clang {
|
|||
REDECLS_UPDATE_LATEST = 29,
|
||||
|
||||
/// \brief Record code for declarations that Sema keeps references of.
|
||||
SEMA_DECL_REFS = 30
|
||||
SEMA_DECL_REFS = 30,
|
||||
|
||||
/// \brief Record code for weak undeclared identifiers.
|
||||
WEAK_UNDECLARED_IDENTIFIERS = 31
|
||||
};
|
||||
|
||||
/// \brief Record types used within a source manager block.
|
||||
|
|
|
@ -379,6 +379,9 @@ private:
|
|||
/// \brief The set of unused static functions stored in the the PCH
|
||||
/// file.
|
||||
llvm::SmallVector<uint64_t, 16> UnusedStaticFuncs;
|
||||
|
||||
/// \brief The set of weak undeclared identifiers stored in the the PCH file.
|
||||
llvm::SmallVector<uint64_t, 64> WeakUndeclaredIdentifiers;
|
||||
|
||||
/// \brief The set of locally-scoped external declarations stored in
|
||||
/// the the PCH file.
|
||||
|
|
|
@ -1642,6 +1642,15 @@ PCHReader::ReadPCHBlock(PerFileData &F) {
|
|||
Record.begin(), Record.end());
|
||||
break;
|
||||
|
||||
case pch::WEAK_UNDECLARED_IDENTIFIERS:
|
||||
// Optimization for the first block.
|
||||
if (WeakUndeclaredIdentifiers.empty())
|
||||
WeakUndeclaredIdentifiers.swap(Record);
|
||||
else
|
||||
WeakUndeclaredIdentifiers.insert(WeakUndeclaredIdentifiers.end(),
|
||||
Record.begin(), Record.end());
|
||||
break;
|
||||
|
||||
case pch::LOCALLY_SCOPED_EXTERNAL_DECLS:
|
||||
// Optimization for the first block.
|
||||
if (LocallyScopedExternalDecls.empty())
|
||||
|
@ -3131,6 +3140,21 @@ void PCHReader::InitializeSema(Sema &S) {
|
|||
SemaObj->UnusedStaticFuncs.push_back(FD);
|
||||
}
|
||||
|
||||
// If there were any weak undeclared identifiers, deserialize them and add to
|
||||
// Sema's list of weak undeclared identifiers.
|
||||
if (!WeakUndeclaredIdentifiers.empty()) {
|
||||
unsigned Idx = 0;
|
||||
for (unsigned I = 0, N = WeakUndeclaredIdentifiers[Idx++]; I != N; ++I) {
|
||||
IdentifierInfo *WeakId = GetIdentifierInfo(WeakUndeclaredIdentifiers,Idx);
|
||||
IdentifierInfo *AliasId=GetIdentifierInfo(WeakUndeclaredIdentifiers,Idx);
|
||||
SourceLocation Loc = ReadSourceLocation(WeakUndeclaredIdentifiers, Idx);
|
||||
bool Used = WeakUndeclaredIdentifiers[Idx++];
|
||||
Sema::WeakInfo WI(AliasId, Loc);
|
||||
WI.setUsed(Used);
|
||||
SemaObj->WeakUndeclaredIdentifiers.insert(std::make_pair(WeakId, WI));
|
||||
}
|
||||
}
|
||||
|
||||
// If there were any locally-scoped external declarations,
|
||||
// deserialize them and add them to Sema's table of locally-scoped
|
||||
// external declarations.
|
||||
|
|
|
@ -2207,6 +2207,20 @@ void PCHWriter::WritePCHCore(Sema &SemaRef, MemorizeStatCalls *StatCalls,
|
|||
RecordData UnusedStaticFuncs;
|
||||
for (unsigned i=0, e = SemaRef.UnusedStaticFuncs.size(); i !=e; ++i)
|
||||
AddDeclRef(SemaRef.UnusedStaticFuncs[i], UnusedStaticFuncs);
|
||||
|
||||
RecordData WeakUndeclaredIdentifiers;
|
||||
if (!SemaRef.WeakUndeclaredIdentifiers.empty()) {
|
||||
WeakUndeclaredIdentifiers.push_back(
|
||||
SemaRef.WeakUndeclaredIdentifiers.size());
|
||||
for (llvm::DenseMap<IdentifierInfo*,Sema::WeakInfo>::iterator
|
||||
I = SemaRef.WeakUndeclaredIdentifiers.begin(),
|
||||
E = SemaRef.WeakUndeclaredIdentifiers.end(); I != E; ++I) {
|
||||
AddIdentifierRef(I->first, WeakUndeclaredIdentifiers);
|
||||
AddIdentifierRef(I->second.getAlias(), WeakUndeclaredIdentifiers);
|
||||
AddSourceLocation(I->second.getLocation(), WeakUndeclaredIdentifiers);
|
||||
WeakUndeclaredIdentifiers.push_back(I->second.getUsed());
|
||||
}
|
||||
}
|
||||
|
||||
// Build a record containing all of the locally-scoped external
|
||||
// declarations in this header file. Generally, this record will be
|
||||
|
@ -2311,6 +2325,11 @@ void PCHWriter::WritePCHCore(Sema &SemaRef, MemorizeStatCalls *StatCalls,
|
|||
if (!UnusedStaticFuncs.empty())
|
||||
Stream.EmitRecord(pch::UNUSED_STATIC_FUNCS, UnusedStaticFuncs);
|
||||
|
||||
// Write the record containing weak undeclared identifiers.
|
||||
if (!WeakUndeclaredIdentifiers.empty())
|
||||
Stream.EmitRecord(pch::WEAK_UNDECLARED_IDENTIFIERS,
|
||||
WeakUndeclaredIdentifiers);
|
||||
|
||||
// Write the record containing locally-scoped external definitions.
|
||||
if (!LocallyScopedExternalDecls.empty())
|
||||
Stream.EmitRecord(pch::LOCALLY_SCOPED_EXTERNAL_DECLS,
|
||||
|
|
|
@ -243,6 +243,9 @@ void Sema::ActOnEndOfTranslationUnit() {
|
|||
true)),
|
||||
UnusedStaticFuncs.end());
|
||||
|
||||
if (!CompleteTranslationUnit)
|
||||
return;
|
||||
|
||||
// Check for #pragma weak identifiers that were never declared
|
||||
// FIXME: This will cause diagnostics to be emitted in a non-determinstic
|
||||
// order! Iterating over a densemap like this is bad.
|
||||
|
@ -255,9 +258,6 @@ void Sema::ActOnEndOfTranslationUnit() {
|
|||
<< I->first;
|
||||
}
|
||||
|
||||
if (!CompleteTranslationUnit)
|
||||
return;
|
||||
|
||||
// C99 6.9.2p2:
|
||||
// A declaration of an identifier for an object that has file
|
||||
// scope without an initializer, and without a storage-class
|
||||
|
|
|
@ -0,0 +1,10 @@
|
|||
// Test this without pch.
|
||||
// RUN: %clang_cc1 -include %S/pragma-weak.h %s -verify -emit-llvm -o - | FileCheck %s
|
||||
|
||||
// Test with pch.
|
||||
// RUN: %clang_cc1 -x c-header -emit-pch -o %t %S/pragma-weak.h
|
||||
// RUN: %clang_cc1 -include-pch %t %s -verify -emit-llvm -o - | FileCheck %s
|
||||
|
||||
// CHECK: @weakvar = weak global i32 0
|
||||
int weakvar;
|
||||
// expected-warning {{weak identifier 'undeclaredvar' never declared}}
|
|
@ -0,0 +1,10 @@
|
|||
// Header for PCH test pragma-weak.c
|
||||
|
||||
#pragma weak weakvar
|
||||
|
||||
|
||||
|
||||
|
||||
|
||||
|
||||
#pragma weak undeclaredvar
|
Loading…
Reference in New Issue