File indexing completed on 2026-05-10 08:36:53
0001
0002
0003
0004
0005
0006
0007
0008
0009 #ifndef LLVM_CLANG_EDIT_EDITEDSOURCE_H
0010 #define LLVM_CLANG_EDIT_EDITEDSOURCE_H
0011
0012 #include "clang/Basic/IdentifierTable.h"
0013 #include "clang/Basic/LLVM.h"
0014 #include "clang/Basic/SourceLocation.h"
0015 #include "clang/Edit/FileOffset.h"
0016 #include "llvm/ADT/DenseMap.h"
0017 #include "llvm/ADT/SmallVector.h"
0018 #include "llvm/ADT/StringRef.h"
0019 #include "llvm/Support/Allocator.h"
0020 #include <map>
0021 #include <tuple>
0022 #include <utility>
0023
0024 namespace clang {
0025
0026 class LangOptions;
0027 class PPConditionalDirectiveRecord;
0028 class SourceManager;
0029
0030 namespace edit {
0031
0032 class Commit;
0033 class EditsReceiver;
0034
0035 class EditedSource {
0036 const SourceManager &SourceMgr;
0037 const LangOptions &LangOpts;
0038 const PPConditionalDirectiveRecord *PPRec;
0039
0040 struct FileEdit {
0041 StringRef Text;
0042 unsigned RemoveLen = 0;
0043
0044 FileEdit() = default;
0045 };
0046
0047 using FileEditsTy = std::map<FileOffset, FileEdit>;
0048
0049 FileEditsTy FileEdits;
0050
0051 struct MacroArgUse {
0052 IdentifierInfo *Identifier;
0053 SourceLocation ImmediateExpansionLoc;
0054
0055
0056 SourceLocation UseLoc;
0057
0058 bool operator==(const MacroArgUse &Other) const {
0059 return std::tie(Identifier, ImmediateExpansionLoc, UseLoc) ==
0060 std::tie(Other.Identifier, Other.ImmediateExpansionLoc,
0061 Other.UseLoc);
0062 }
0063 };
0064
0065 llvm::DenseMap<SourceLocation, SmallVector<MacroArgUse, 2>> ExpansionToArgMap;
0066 SmallVector<std::pair<SourceLocation, MacroArgUse>, 2>
0067 CurrCommitMacroArgExps;
0068
0069 IdentifierTable IdentTable;
0070 llvm::BumpPtrAllocator StrAlloc;
0071
0072 public:
0073 EditedSource(const SourceManager &SM, const LangOptions &LangOpts,
0074 const PPConditionalDirectiveRecord *PPRec = nullptr)
0075 : SourceMgr(SM), LangOpts(LangOpts), PPRec(PPRec), IdentTable(LangOpts) {}
0076
0077 const SourceManager &getSourceManager() const { return SourceMgr; }
0078 const LangOptions &getLangOpts() const { return LangOpts; }
0079
0080 const PPConditionalDirectiveRecord *getPPCondDirectiveRecord() const {
0081 return PPRec;
0082 }
0083
0084 bool canInsertInOffset(SourceLocation OrigLoc, FileOffset Offs);
0085
0086 bool commit(const Commit &commit);
0087
0088 void applyRewrites(EditsReceiver &receiver, bool adjustRemovals = true);
0089 void clearRewrites();
0090
0091 StringRef copyString(StringRef str) { return str.copy(StrAlloc); }
0092 StringRef copyString(const Twine &twine);
0093
0094 private:
0095 bool commitInsert(SourceLocation OrigLoc, FileOffset Offs, StringRef text,
0096 bool beforePreviousInsertions);
0097 bool commitInsertFromRange(SourceLocation OrigLoc, FileOffset Offs,
0098 FileOffset InsertFromRangeOffs, unsigned Len,
0099 bool beforePreviousInsertions);
0100 void commitRemove(SourceLocation OrigLoc, FileOffset BeginOffs, unsigned Len);
0101
0102 StringRef getSourceText(FileOffset BeginOffs, FileOffset EndOffs,
0103 bool &Invalid);
0104 FileEditsTy::iterator getActionForOffset(FileOffset Offs);
0105 void deconstructMacroArgLoc(SourceLocation Loc,
0106 SourceLocation &ExpansionLoc,
0107 MacroArgUse &ArgUse);
0108
0109 void startingCommit();
0110 void finishedCommit();
0111 };
0112
0113 }
0114
0115 }
0116
0117 #endif