blob: 4880c8106a45fdba0ff3d8eb12bd0c79188ed494 [file] [log] [blame]
Alex Lorenzee024992014-08-04 18:41:51 +00001//===--- CoverageMappingGen.cpp - Coverage mapping generation ---*- C++ -*-===//
2//
3// The LLVM Compiler Infrastructure
4//
5// This file is distributed under the University of Illinois Open Source
6// License. See LICENSE.TXT for details.
7//
8//===----------------------------------------------------------------------===//
9//
10// Instrumentation-based code coverage mapping generator
11//
12//===----------------------------------------------------------------------===//
13
14#include "CoverageMappingGen.h"
15#include "CodeGenFunction.h"
16#include "clang/AST/StmtVisitor.h"
17#include "clang/Lex/Lexer.h"
18#include "llvm/ProfileData/InstrProfReader.h"
19#include "llvm/ProfileData/CoverageMapping.h"
20#include "llvm/ProfileData/CoverageMappingWriter.h"
Alex Lorenzf2cf38e2014-08-08 23:41:24 +000021#include "llvm/ProfileData/CoverageMappingReader.h"
Alex Lorenzee024992014-08-04 18:41:51 +000022#include "llvm/Support/FileSystem.h"
23
24using namespace clang;
25using namespace CodeGen;
26using namespace llvm::coverage;
27
28void CoverageSourceInfo::SourceRangeSkipped(SourceRange Range) {
29 SkippedRanges.push_back(Range);
30}
31
32namespace {
33
34/// \brief A region of source code that can be mapped to a counter.
35struct SourceMappingRegion {
36 enum RegionFlags {
37 /// \brief This region won't be emitted if it wasn't extended.
38 /// This is useful so that we won't emit source ranges for single tokens
39 /// that we don't really care that much about, like:
40 /// the '(' token in #define MACRO (
41 IgnoreIfNotExtended = 0x0001,
42 };
43
44 FileID File, MacroArgumentFile;
45
46 Counter Count;
47
48 /// \brief A statement that initiated the count of Zero.
49 ///
50 /// This initiator statement is useful to prevent merging of unreachable
51 /// regions with different statements that caused the counter to become
52 /// unreachable.
53 const Stmt *UnreachableInitiator;
54
55 /// \brief A statement that separates certain mapping regions into groups.
56 ///
57 /// The group statement is sometimes useful when we are emitting the source
58 /// regions not in their correct lexical order, e.g. the regions for the
59 /// incrementation expression in the 'for' construct. By marking the regions
60 /// in the incrementation expression with the group statement, we avoid the
61 /// merging of the regions from the incrementation expression and the loop's
62 /// body.
63 const Stmt *Group;
64
65 /// \brief The region's starting location.
66 SourceLocation LocStart;
67
68 /// \brief The region's ending location.
69 SourceLocation LocEnd, AlternativeLocEnd;
70 unsigned Flags;
71 CounterMappingRegion::RegionKind Kind;
72
73 SourceMappingRegion(FileID File, FileID MacroArgumentFile, Counter Count,
74 const Stmt *UnreachableInitiator, const Stmt *Group,
75 SourceLocation LocStart, SourceLocation LocEnd,
76 unsigned Flags = 0,
77 CounterMappingRegion::RegionKind Kind =
78 CounterMappingRegion::CodeRegion)
79 : File(File), MacroArgumentFile(MacroArgumentFile), Count(Count),
80 UnreachableInitiator(UnreachableInitiator), Group(Group),
81 LocStart(LocStart), LocEnd(LocEnd), AlternativeLocEnd(LocStart),
82 Flags(Flags), Kind(Kind) {}
83
84 bool hasFlag(RegionFlags Flag) const { return (Flags & Flag) != 0; }
85
86 void setFlag(RegionFlags Flag) { Flags |= Flag; }
87
88 void clearFlag(RegionFlags Flag) { Flags &= ~Flag; }
89
90 /// \brief Return true if two regions can be merged together.
91 bool isMergeable(SourceMappingRegion &R) {
92 return File == R.File && MacroArgumentFile == R.MacroArgumentFile &&
93 Count == R.Count && UnreachableInitiator == R.UnreachableInitiator &&
94 Group == R.Group && Kind == R.Kind;
95 }
96
97 /// \brief Merge two regions by extending the 'this' region to cover the
98 /// given region.
99 void mergeByExtendingTo(SourceMappingRegion &R) {
100 LocEnd = R.LocEnd;
101 AlternativeLocEnd = R.LocStart;
102 if (hasFlag(IgnoreIfNotExtended))
103 clearFlag(IgnoreIfNotExtended);
104 }
105};
106
107/// \brief The state of the coverage mapping builder.
108struct SourceMappingState {
109 Counter CurrentRegionCount;
110 const Stmt *CurrentSourceGroup;
111 const Stmt *CurrentUnreachableRegionInitiator;
112
113 SourceMappingState(Counter CurrentRegionCount, const Stmt *CurrentSourceGroup,
114 const Stmt *CurrentUnreachableRegionInitiator)
115 : CurrentRegionCount(CurrentRegionCount),
116 CurrentSourceGroup(CurrentSourceGroup),
117 CurrentUnreachableRegionInitiator(CurrentUnreachableRegionInitiator) {}
118};
119
120/// \brief Provides the common functionality for the different
121/// coverage mapping region builders.
122class CoverageMappingBuilder {
123public:
124 CoverageMappingModuleGen &CVM;
125 SourceManager &SM;
126 const LangOptions &LangOpts;
127
128private:
129 struct FileInfo {
130 /// \brief The file id that will be used by the coverage mapping system.
131 unsigned CovMappingFileID;
132 const FileEntry *Entry;
133
134 FileInfo(unsigned CovMappingFileID, const FileEntry *Entry)
135 : CovMappingFileID(CovMappingFileID), Entry(Entry) {}
136 };
137
138 /// \brief This mapping maps clang's FileIDs to file ids used
139 /// by the coverage mapping system and clang's file entries.
140 llvm::SmallDenseMap<FileID, FileInfo, 8> FileIDMapping;
141
142public:
143 /// \brief The statement that corresponds to the current source group.
144 const Stmt *CurrentSourceGroup;
145
146 /// \brief The statement the initiated the current unreachable region.
147 const Stmt *CurrentUnreachableRegionInitiator;
148
149 /// \brief The coverage mapping regions for this function
150 llvm::SmallVector<CounterMappingRegion, 32> MappingRegions;
151 /// \brief The source mapping regions for this function.
152 llvm::SmallVector<SourceMappingRegion, 32> SourceRegions;
153
154 CoverageMappingBuilder(CoverageMappingModuleGen &CVM, SourceManager &SM,
155 const LangOptions &LangOpts)
156 : CVM(CVM), SM(SM), LangOpts(LangOpts),
157 CurrentSourceGroup(nullptr),
158 CurrentUnreachableRegionInitiator(nullptr) {}
159
160 /// \brief Return the precise end location for the given token.
161 SourceLocation getPreciseTokenLocEnd(SourceLocation Loc) {
162 return Lexer::getLocForEndOfToken(SM.getSpellingLoc(Loc), 0, SM, LangOpts);
163 }
164
165 /// \brief Create the mapping that maps from the function's file ids to
166 /// the indices for the translation unit's filenames.
167 void createFileIDMapping(SmallVectorImpl<unsigned> &Mapping) {
168 Mapping.resize(FileIDMapping.size(), 0);
169 for (const auto &I : FileIDMapping)
170 Mapping[I.second.CovMappingFileID] = CVM.getFileID(I.second.Entry);
171 }
172
173 /// \brief Get the coverage mapping file id that corresponds to the given
174 /// clang file id. If such file id doesn't exist, it gets added to the
175 /// mapping that maps from clang's file ids to coverage mapping file ids.
176 /// Return true if there was an error getting the coverage mapping file id.
177 /// An example of an when this function fails is when the region tries
178 /// to get a coverage file id for a location in a built-in macro.
179 bool getCoverageFileID(SourceLocation LocStart, FileID File,
180 FileID SpellingFile, unsigned &Result) {
181 auto Mapping = FileIDMapping.find(File);
182 if (Mapping != FileIDMapping.end()) {
183 Result = Mapping->second.CovMappingFileID;
184 return false;
185 }
186
187 auto Entry = SM.getFileEntryForID(SpellingFile);
188 if (!Entry)
189 return true;
190
191 Result = FileIDMapping.size();
192 FileIDMapping.insert(std::make_pair(File, FileInfo(Result, Entry)));
193 createFileExpansionRegion(LocStart, File);
194 return false;
195 }
196
197 /// \brief Get the coverage mapping file id that corresponds to the given
198 /// clang file id.
199 /// Return true if there was an error getting the coverage mapping file id.
200 bool getExistingCoverageFileID(FileID File, unsigned &Result) {
201 // Make sure that the file is valid.
202 if (File.isInvalid())
203 return true;
204 auto Mapping = FileIDMapping.find(File);
205 if (Mapping != FileIDMapping.end()) {
206 Result = Mapping->second.CovMappingFileID;
207 return false;
208 }
209 return true;
210 }
211
212 /// \brief Return true if the given clang's file id has a corresponding
213 /// coverage file id.
214 bool hasExistingCoverageFileID(FileID File) const {
215 return FileIDMapping.count(File);
216 }
217
218 /// \brief Gather all the regions that were skipped by the preprocessor
219 /// using the constructs like #if.
220 void gatherSkippedRegions() {
221 /// An array of the minimum lineStarts and the maximum lineEnds
222 /// for mapping regions from the appropriate source files.
223 llvm::SmallVector<std::pair<unsigned, unsigned>, 8> FileLineRanges;
224 FileLineRanges.resize(
225 FileIDMapping.size(),
226 std::make_pair(std::numeric_limits<unsigned>::max(), 0));
227 for (const auto &R : MappingRegions) {
228 FileLineRanges[R.FileID].first =
229 std::min(FileLineRanges[R.FileID].first, R.LineStart);
230 FileLineRanges[R.FileID].second =
231 std::max(FileLineRanges[R.FileID].second, R.LineEnd);
232 }
233
234 auto SkippedRanges = CVM.getSourceInfo().getSkippedRanges();
235 for (const auto &I : SkippedRanges) {
236 auto LocStart = I.getBegin();
237 auto LocEnd = I.getEnd();
238 auto FileStart = SM.getFileID(LocStart);
239 if (!hasExistingCoverageFileID(FileStart))
240 continue;
241 auto ActualFileStart = SM.getDecomposedSpellingLoc(LocStart).first;
242 if (ActualFileStart != SM.getDecomposedSpellingLoc(LocEnd).first)
243 // Ignore regions that span across multiple files.
244 continue;
245
246 unsigned CovFileID;
247 if (getCoverageFileID(LocStart, FileStart, ActualFileStart, CovFileID))
248 continue;
249 unsigned LineStart = SM.getSpellingLineNumber(LocStart);
250 unsigned ColumnStart = SM.getSpellingColumnNumber(LocStart);
251 unsigned LineEnd = SM.getSpellingLineNumber(LocEnd);
252 unsigned ColumnEnd = SM.getSpellingColumnNumber(LocEnd);
253 CounterMappingRegion Region(Counter(), CovFileID, LineStart, ColumnStart,
254 LineEnd, ColumnEnd, false,
255 CounterMappingRegion::SkippedRegion);
256 // Make sure that we only collect the regions that are inside
257 // the souce code of this function.
258 if (Region.LineStart >= FileLineRanges[CovFileID].first &&
259 Region.LineEnd <= FileLineRanges[CovFileID].second)
260 MappingRegions.push_back(Region);
261 }
262 }
263
264 /// \brief Create a mapping region that correponds to an expansion of
265 /// a macro or an embedded include.
266 void createFileExpansionRegion(SourceLocation Loc, FileID ExpandedFile) {
267 SourceLocation LocStart;
268 if (Loc.isMacroID())
269 LocStart = SM.getImmediateExpansionRange(Loc).first;
270 else {
271 LocStart = SM.getIncludeLoc(ExpandedFile);
272 if (LocStart.isInvalid())
273 return; // This file has no expansion region.
274 }
275
276 auto File = SM.getFileID(LocStart);
277 auto SpellingFile = SM.getDecomposedSpellingLoc(LocStart).first;
278 unsigned CovFileID, ExpandedFileID;
279 if (getExistingCoverageFileID(ExpandedFile, ExpandedFileID))
280 return;
281 if (getCoverageFileID(LocStart, File, SpellingFile, CovFileID))
282 return;
283 unsigned LineStart = SM.getSpellingLineNumber(LocStart);
284 unsigned ColumnStart = SM.getSpellingColumnNumber(LocStart);
285 unsigned LineEnd = LineStart;
286 // Compute the end column manually as Lexer::getLocForEndOfToken doesn't
287 // give the correct result in all cases.
288 unsigned ColumnEnd =
289 ColumnStart +
290 Lexer::MeasureTokenLength(SM.getSpellingLoc(LocStart), SM, LangOpts);
291
292 MappingRegions.push_back(CounterMappingRegion(
293 Counter(), CovFileID, LineStart, ColumnStart, LineEnd, ColumnEnd,
294 false, CounterMappingRegion::ExpansionRegion));
295 MappingRegions.back().ExpandedFileID = ExpandedFileID;
296 }
297
298 /// \brief Enter a source region group that is identified by the given
299 /// statement.
300 /// It's not possible to enter a group when there is already
301 /// another group present.
302 void beginSourceRegionGroup(const Stmt *Group) {
303 assert(!CurrentSourceGroup);
304 CurrentSourceGroup = Group;
305 }
306
307 /// \brief Exit the current source region group.
308 void endSourceRegionGroup() { CurrentSourceGroup = nullptr; }
309
310 /// \brief Brings a region that has the same counter and file to the back
311 /// of the source regions array.
312 void bringSimilarRegionBack(Counter Count, FileID File,
313 FileID MacroArgumentFile,
314 const Stmt *UnreachableInitiator,
315 const Stmt *SourceGroup) {
316 for (size_t I = SourceRegions.size(); I != 0;) {
317 --I;
318 if (SourceRegions[I].Count == Count && SourceRegions[I].File == File &&
319 SourceRegions[I].MacroArgumentFile == MacroArgumentFile &&
320 SourceRegions[I].UnreachableInitiator == UnreachableInitiator &&
321 SourceRegions[I].Group == SourceGroup) {
322 if (I != SourceRegions.size() - 1)
323 std::swap(SourceRegions[I], SourceRegions.back());
324 return;
325 }
326 }
327 }
328
329 /// \brief Associate a counter with a given source code range.
330 void mapSourceCodeRange(SourceLocation LocStart, SourceLocation LocEnd,
331 Counter Count, const Stmt *UnreachableInitiator,
332 const Stmt *SourceGroup, unsigned Flags = 0,
333 FileID MacroArgumentFile = FileID()) {
334 if (SM.isMacroArgExpansion(LocStart)) {
335 // Map the code range with the macro argument's value.
336 mapSourceCodeRange(SM.getImmediateSpellingLoc(LocStart),
337 SM.getImmediateSpellingLoc(LocEnd), Count,
338 UnreachableInitiator, SourceGroup, Flags,
339 SM.getFileID(LocStart));
340 // Map the code range where the macro argument is referenced.
341 SourceLocation RefLocStart(SM.getImmediateExpansionRange(LocStart).first);
342 SourceLocation RefLocEnd(RefLocStart);
343 if (SM.isMacroArgExpansion(RefLocStart))
344 mapSourceCodeRange(RefLocStart, RefLocEnd, Count, UnreachableInitiator,
345 SourceGroup, 0, SM.getFileID(RefLocStart));
346 else
347 mapSourceCodeRange(RefLocStart, RefLocEnd, Count, UnreachableInitiator,
348 SourceGroup);
349 return;
350 }
351 auto File = SM.getFileID(LocStart);
352 // Make sure that the file id is valid.
353 if (File.isInvalid())
354 return;
355 bringSimilarRegionBack(Count, File, MacroArgumentFile, UnreachableInitiator,
356 SourceGroup);
357 SourceMappingRegion R(File, MacroArgumentFile, Count, UnreachableInitiator,
358 SourceGroup, LocStart, LocEnd, Flags);
359 if (SourceRegions.empty() || !SourceRegions.back().isMergeable(R)) {
360 SourceRegions.push_back(R);
361 return;
362 }
363 SourceRegions.back().mergeByExtendingTo(R);
364 }
365
366 void mapSourceCodeRange(SourceLocation LocStart, SourceLocation LocEnd,
367 Counter Count, unsigned Flags = 0) {
368 mapSourceCodeRange(LocStart, LocEnd, Count,
369 CurrentUnreachableRegionInitiator, CurrentSourceGroup,
370 Flags);
371 }
372
373 void mapSourceCodeRange(const SourceMappingState &State,
374 SourceLocation LocStart, SourceLocation LocEnd,
375 unsigned Flags = 0) {
376 mapSourceCodeRange(LocStart, LocEnd, State.CurrentRegionCount,
377 State.CurrentUnreachableRegionInitiator,
378 State.CurrentSourceGroup, Flags);
379 }
380
381 /// \brief Generate the coverage counter mapping regions from collected
382 /// source regions.
383 void emitSourceRegions() {
384 for (const auto &R : SourceRegions) {
385 SourceLocation LocStart = R.LocStart;
386 SourceLocation LocEnd = R.LocEnd;
387 if (SM.getFileID(LocEnd) != R.File)
388 LocEnd = R.AlternativeLocEnd;
389
390 if (R.hasFlag(SourceMappingRegion::IgnoreIfNotExtended) &&
391 LocStart == LocEnd)
392 continue;
393
394 LocEnd = getPreciseTokenLocEnd(LocEnd);
395 unsigned LineStart = SM.getSpellingLineNumber(LocStart);
396 unsigned ColumnStart = SM.getSpellingColumnNumber(LocStart);
397 unsigned LineEnd = SM.getSpellingLineNumber(LocEnd);
398 unsigned ColumnEnd = SM.getSpellingColumnNumber(LocEnd);
399
400 auto SpellingFile = SM.getDecomposedSpellingLoc(R.LocStart).first;
401 unsigned CovFileID;
402 if (getCoverageFileID(R.LocStart, R.File, SpellingFile, CovFileID))
403 continue;
404
405 assert(LineStart <= LineEnd);
406 MappingRegions.push_back(CounterMappingRegion(
407 R.Count, CovFileID, LineStart, ColumnStart, LineEnd, ColumnEnd,
408 false, CounterMappingRegion::CodeRegion));
409 }
410 }
411};
412
413/// \brief Creates unreachable coverage regions for the functions that
414/// are not emitted.
415struct EmptyCoverageMappingBuilder : public CoverageMappingBuilder {
416 EmptyCoverageMappingBuilder(CoverageMappingModuleGen &CVM, SourceManager &SM,
417 const LangOptions &LangOpts)
418 : CoverageMappingBuilder(CVM, SM, LangOpts) {}
419
420 void VisitDecl(const Decl *D) {
421 if (!D->hasBody())
422 return;
423 auto Body = D->getBody();
424 mapSourceCodeRange(Body->getLocStart(), Body->getLocEnd(), Counter());
425 }
426
427 /// \brief Write the mapping data to the output stream
428 void write(llvm::raw_ostream &OS) {
429 emitSourceRegions();
430 SmallVector<unsigned, 16> FileIDMapping;
431 createFileIDMapping(FileIDMapping);
432
Craig Topper5fc8fc22014-08-27 06:28:36 +0000433 CoverageMappingWriter Writer(FileIDMapping, None, MappingRegions);
Alex Lorenzee024992014-08-04 18:41:51 +0000434 Writer.write(OS);
435 }
436};
437
438/// \brief A StmtVisitor that creates coverage mapping regions which map
439/// from the source code locations to the PGO counters.
440struct CounterCoverageMappingBuilder
441 : public CoverageMappingBuilder,
442 public ConstStmtVisitor<CounterCoverageMappingBuilder> {
443 /// \brief The map of statements to count values.
444 llvm::DenseMap<const Stmt *, unsigned> &CounterMap;
445
446 Counter CurrentRegionCount;
447
448 CounterExpressionBuilder Builder;
449
450 /// \brief Return a counter that represents the
451 /// expression that subracts rhs from lhs.
452 Counter subtractCounters(Counter LHS, Counter RHS) {
453 return Builder.subtract(LHS, RHS);
454 }
455
456 /// \brief Return a counter that represents the
457 /// the exression that adds lhs and rhs.
458 Counter addCounters(Counter LHS, Counter RHS) {
459 return Builder.add(LHS, RHS);
460 }
461
462 /// \brief Return the region counter for the given statement.
463 /// This should only be called on statements that have a dedicated counter.
464 unsigned getRegionCounter(const Stmt *S) { return CounterMap[S]; }
465
466 /// \brief Return the region count for the counter at the given index.
467 Counter getRegionCount(unsigned CounterId) {
468 return Counter::getCounter(CounterId);
469 }
470
471 /// \brief Return the counter value of the current region.
472 Counter getCurrentRegionCount() { return CurrentRegionCount; }
473
474 /// \brief Set the counter value for the current region.
475 /// This is used to keep track of changes to the most recent counter
476 /// from control flow and non-local exits.
477 void setCurrentRegionCount(Counter Count) {
478 CurrentRegionCount = Count;
479 CurrentUnreachableRegionInitiator = nullptr;
480 }
481
482 /// \brief Indicate that the current region is never reached,
483 /// and thus should have a counter value of zero.
484 /// This is important so that subsequent regions can correctly track
485 /// their parent counts.
486 void setCurrentRegionUnreachable(const Stmt *Initiator) {
487 CurrentRegionCount = Counter::getZero();
488 CurrentUnreachableRegionInitiator = Initiator;
489 }
490
491 /// \brief A counter for a particular region.
492 /// This is the primary interface through
493 /// which the coverage mapping builder manages counters and their values.
494 class RegionMapper {
495 CounterCoverageMappingBuilder &Mapping;
496 Counter Count;
497 Counter ParentCount;
498 Counter RegionCount;
499 Counter Adjust;
500
501 public:
502 RegionMapper(CounterCoverageMappingBuilder *Mapper, const Stmt *S)
503 : Mapping(*Mapper),
504 Count(Mapper->getRegionCount(Mapper->getRegionCounter(S))),
505 ParentCount(Mapper->getCurrentRegionCount()) {}
506
507 /// Get the value of the counter. In most cases this is the number of times
508 /// the region of the counter was entered, but for switch labels it's the
509 /// number of direct jumps to that label.
510 Counter getCount() const { return Count; }
511
512 /// Get the value of the counter with adjustments applied. Adjustments occur
513 /// when control enters or leaves the region abnormally; i.e., if there is a
514 /// jump to a label within the region, or if the function can return from
515 /// within the region. The adjusted count, then, is the value of the counter
516 /// at the end of the region.
517 Counter getAdjustedCount() const {
518 return Mapping.addCounters(Count, Adjust);
519 }
520
521 /// Get the value of the counter in this region's parent, i.e., the region
522 /// that was active when this region began. This is useful for deriving
523 /// counts in implicitly counted regions, like the false case of a condition
524 /// or the normal exits of a loop.
525 Counter getParentCount() const { return ParentCount; }
526
527 /// Activate the counter by emitting an increment and starting to track
528 /// adjustments. If AddIncomingFallThrough is true, the current region count
529 /// will be added to the counter for the purposes of tracking the region.
530 void beginRegion(bool AddIncomingFallThrough = false) {
531 RegionCount = Count;
532 if (AddIncomingFallThrough)
533 RegionCount =
534 Mapping.addCounters(RegionCount, Mapping.getCurrentRegionCount());
535 Mapping.setCurrentRegionCount(RegionCount);
536 }
537
538 /// For counters on boolean branches, begins tracking adjustments for the
539 /// uncounted path.
540 void beginElseRegion() {
541 RegionCount = Mapping.subtractCounters(ParentCount, Count);
542 Mapping.setCurrentRegionCount(RegionCount);
543 }
544
545 /// Reset the current region count.
546 void setCurrentRegionCount(Counter CurrentCount) {
547 RegionCount = CurrentCount;
548 Mapping.setCurrentRegionCount(RegionCount);
549 }
550
551 /// Adjust for non-local control flow after emitting a subexpression or
552 /// substatement. This must be called to account for constructs such as
553 /// gotos,
554 /// labels, and returns, so that we can ensure that our region's count is
555 /// correct in the code that follows.
556 void adjustForControlFlow() {
557 Adjust = Mapping.addCounters(
558 Adjust, Mapping.subtractCounters(Mapping.getCurrentRegionCount(),
559 RegionCount));
560 // Reset the region count in case this is called again later.
561 RegionCount = Mapping.getCurrentRegionCount();
562 }
563
564 /// Commit all adjustments to the current region. If the region is a loop,
565 /// the LoopAdjust value should be the count of all the breaks and continues
566 /// from the loop, to compensate for those counts being deducted from the
567 /// adjustments for the body of the loop.
568 void applyAdjustmentsToRegion() {
569 Mapping.setCurrentRegionCount(Mapping.addCounters(ParentCount, Adjust));
570 }
571 void applyAdjustmentsToRegion(Counter LoopAdjust) {
572 Mapping.setCurrentRegionCount(Mapping.addCounters(
573 Mapping.addCounters(ParentCount, Adjust), LoopAdjust));
574 }
575 };
576
577 /// \brief Keep counts of breaks and continues inside loops.
578 struct BreakContinue {
579 Counter BreakCount;
580 Counter ContinueCount;
581 };
582 SmallVector<BreakContinue, 8> BreakContinueStack;
583
584 CounterCoverageMappingBuilder(
585 CoverageMappingModuleGen &CVM,
586 llvm::DenseMap<const Stmt *, unsigned> &CounterMap,
587 unsigned NumRegionCounters, SourceManager &SM,
588 const LangOptions &LangOpts)
589 : CoverageMappingBuilder(CVM, SM, LangOpts), CounterMap(CounterMap),
590 Builder(NumRegionCounters) {}
591
592 /// \brief Write the mapping data to the output stream
593 void write(llvm::raw_ostream &OS) {
594 emitSourceRegions();
595 llvm::SmallVector<unsigned, 8> VirtualFileMapping;
596 createFileIDMapping(VirtualFileMapping);
597 gatherSkippedRegions();
598
599 CoverageMappingWriter Writer(
600 VirtualFileMapping, Builder.getExpressions(), MappingRegions);
601 Writer.write(OS);
602 }
603
604 /// \brief Return the current source mapping state.
605 SourceMappingState getCurrentState() const {
606 return SourceMappingState(CurrentRegionCount, CurrentSourceGroup,
607 CurrentUnreachableRegionInitiator);
608 }
609
610 /// \brief Associate the source code range with the current region count.
611 void mapSourceCodeRange(SourceLocation LocStart, SourceLocation LocEnd,
612 unsigned Flags = 0) {
613 CoverageMappingBuilder::mapSourceCodeRange(LocStart, LocEnd,
614 CurrentRegionCount, Flags);
615 }
616
617 void mapSourceCodeRange(SourceLocation LocStart) {
618 CoverageMappingBuilder::mapSourceCodeRange(LocStart, LocStart,
619 CurrentRegionCount);
620 }
621
622 /// \brief Associate the source range of a token with the current region
623 /// count.
624 /// Ignore the source range for this token if it produces a distinct
625 /// mapping region with no other source ranges.
626 void mapToken(SourceLocation LocStart) {
627 CoverageMappingBuilder::mapSourceCodeRange(
628 LocStart, LocStart, CurrentRegionCount,
629 SourceMappingRegion::IgnoreIfNotExtended);
630 }
631
632 void mapToken(const SourceMappingState &State, SourceLocation LocStart) {
633 CoverageMappingBuilder::mapSourceCodeRange(
634 State, LocStart, LocStart, SourceMappingRegion::IgnoreIfNotExtended);
635 }
636
637 void VisitStmt(const Stmt *S) {
638 mapSourceCodeRange(S->getLocStart());
639 for (Stmt::const_child_range I = S->children(); I; ++I) {
640 if (*I)
641 this->Visit(*I);
642 }
643 }
644
645 /// \brief If the given statement is a compound statement,
646 /// map '}' with the same count as '{'.
647 void VisitSubStmtRBraceState(const Stmt *S) {
648 if (!isa<CompoundStmt>(S))
649 return Visit(S);
650 const auto *CS = cast<CompoundStmt>(S);
651 auto State = getCurrentState();
652 mapSourceCodeRange(CS->getLBracLoc());
653 for (Stmt::const_child_range I = S->children(); I; ++I) {
654 if (*I)
655 this->Visit(*I);
656 }
657 CoverageMappingBuilder::mapSourceCodeRange(State, CS->getRBracLoc(),
658 CS->getRBracLoc());
659 }
660
661 void VisitDecl(const Decl *D) {
662 if (!D->hasBody())
663 return;
664 // Counter tracks entry to the function body.
665 auto Body = D->getBody();
666 RegionMapper Cnt(this, Body);
667 Cnt.beginRegion();
668 VisitSubStmtRBraceState(Body);
669 }
670
671 void VisitDeclStmt(const DeclStmt *S) {
672 mapSourceCodeRange(S->getLocStart());
673 for (Stmt::const_child_range I = static_cast<const Stmt *>(S)->children();
674 I; ++I) {
675 if (*I)
676 this->Visit(*I);
677 }
678 }
679
680 void VisitCompoundStmt(const CompoundStmt *S) {
681 mapSourceCodeRange(S->getLBracLoc());
682 for (Stmt::const_child_range I = S->children(); I; ++I) {
683 if (*I)
684 this->Visit(*I);
685 }
686 mapSourceCodeRange(S->getRBracLoc(), S->getRBracLoc());
687 }
688
689 void VisitReturnStmt(const ReturnStmt *S) {
690 mapSourceCodeRange(S->getLocStart());
691 if (S->getRetValue())
692 Visit(S->getRetValue());
693 setCurrentRegionUnreachable(S);
694 }
695
696 void VisitGotoStmt(const GotoStmt *S) {
697 mapSourceCodeRange(S->getLocStart());
698 mapToken(S->getLabelLoc());
699 setCurrentRegionUnreachable(S);
700 }
701
702 void VisitLabelStmt(const LabelStmt *S) {
703 // Counter tracks the block following the label.
704 RegionMapper Cnt(this, S);
705 Cnt.beginRegion();
706 mapSourceCodeRange(S->getLocStart());
707 // Can't map the ':' token as its location isn't known.
708 Visit(S->getSubStmt());
709 }
710
711 void VisitBreakStmt(const BreakStmt *S) {
712 mapSourceCodeRange(S->getLocStart());
713 assert(!BreakContinueStack.empty() && "break not in a loop or switch!");
714 BreakContinueStack.back().BreakCount = addCounters(
715 BreakContinueStack.back().BreakCount, getCurrentRegionCount());
716 setCurrentRegionUnreachable(S);
717 }
718
719 void VisitContinueStmt(const ContinueStmt *S) {
720 mapSourceCodeRange(S->getLocStart());
721 assert(!BreakContinueStack.empty() && "continue stmt not in a loop!");
722 BreakContinueStack.back().ContinueCount = addCounters(
723 BreakContinueStack.back().ContinueCount, getCurrentRegionCount());
724 setCurrentRegionUnreachable(S);
725 }
726
727 void VisitWhileStmt(const WhileStmt *S) {
728 mapSourceCodeRange(S->getLocStart());
729 // Counter tracks the body of the loop.
730 RegionMapper Cnt(this, S);
731 BreakContinueStack.push_back(BreakContinue());
732 // Visit the body region first so the break/continue adjustments can be
733 // included when visiting the condition.
734 Cnt.beginRegion();
735 VisitSubStmtRBraceState(S->getBody());
736 Cnt.adjustForControlFlow();
737
738 // ...then go back and propagate counts through the condition. The count
739 // at the start of the condition is the sum of the incoming edges,
740 // the backedge from the end of the loop body, and the edges from
741 // continue statements.
742 BreakContinue BC = BreakContinueStack.pop_back_val();
743 Cnt.setCurrentRegionCount(
744 addCounters(Cnt.getParentCount(),
745 addCounters(Cnt.getAdjustedCount(), BC.ContinueCount)));
746 beginSourceRegionGroup(S->getCond());
747 Visit(S->getCond());
748 endSourceRegionGroup();
749 Cnt.adjustForControlFlow();
750 Cnt.applyAdjustmentsToRegion(addCounters(BC.BreakCount, BC.ContinueCount));
751 }
752
753 void VisitDoStmt(const DoStmt *S) {
754 mapSourceCodeRange(S->getLocStart());
755 // Counter tracks the body of the loop.
756 RegionMapper Cnt(this, S);
757 BreakContinueStack.push_back(BreakContinue());
758 Cnt.beginRegion(/*AddIncomingFallThrough=*/true);
759 VisitSubStmtRBraceState(S->getBody());
760 Cnt.adjustForControlFlow();
761
762 BreakContinue BC = BreakContinueStack.pop_back_val();
763 // The count at the start of the condition is equal to the count at the
764 // end of the body. The adjusted count does not include either the
765 // fall-through count coming into the loop or the continue count, so add
766 // both of those separately. This is coincidentally the same equation as
767 // with while loops but for different reasons.
768 Cnt.setCurrentRegionCount(
769 addCounters(Cnt.getParentCount(),
770 addCounters(Cnt.getAdjustedCount(), BC.ContinueCount)));
771 Visit(S->getCond());
772 Cnt.adjustForControlFlow();
773 Cnt.applyAdjustmentsToRegion(addCounters(BC.BreakCount, BC.ContinueCount));
774 }
775
776 void VisitForStmt(const ForStmt *S) {
777 mapSourceCodeRange(S->getLocStart());
778 if (S->getInit())
779 Visit(S->getInit());
780
781 // Counter tracks the body of the loop.
782 RegionMapper Cnt(this, S);
783 BreakContinueStack.push_back(BreakContinue());
784 // Visit the body region first. (This is basically the same as a while
785 // loop; see further comments in VisitWhileStmt.)
786 Cnt.beginRegion();
787 VisitSubStmtRBraceState(S->getBody());
788 Cnt.adjustForControlFlow();
789
790 // The increment is essentially part of the body but it needs to include
791 // the count for all the continue statements.
792 if (S->getInc()) {
793 Cnt.setCurrentRegionCount(addCounters(
794 getCurrentRegionCount(), BreakContinueStack.back().ContinueCount));
795 beginSourceRegionGroup(S->getInc());
796 Visit(S->getInc());
797 endSourceRegionGroup();
798 Cnt.adjustForControlFlow();
799 }
800
801 BreakContinue BC = BreakContinueStack.pop_back_val();
802
803 // ...then go back and propagate counts through the condition.
804 if (S->getCond()) {
805 Cnt.setCurrentRegionCount(
806 addCounters(addCounters(Cnt.getParentCount(), Cnt.getAdjustedCount()),
807 BC.ContinueCount));
808 beginSourceRegionGroup(S->getCond());
809 Visit(S->getCond());
810 endSourceRegionGroup();
811 Cnt.adjustForControlFlow();
812 }
813 Cnt.applyAdjustmentsToRegion(addCounters(BC.BreakCount, BC.ContinueCount));
814 }
815
816 void VisitCXXForRangeStmt(const CXXForRangeStmt *S) {
817 mapSourceCodeRange(S->getLocStart());
818 Visit(S->getRangeStmt());
819 Visit(S->getBeginEndStmt());
820 // Counter tracks the body of the loop.
821 RegionMapper Cnt(this, S);
822 BreakContinueStack.push_back(BreakContinue());
823 // Visit the body region first. (This is basically the same as a while
824 // loop; see further comments in VisitWhileStmt.)
825 Cnt.beginRegion();
826 VisitSubStmtRBraceState(S->getBody());
827 Cnt.adjustForControlFlow();
828 BreakContinue BC = BreakContinueStack.pop_back_val();
829 Cnt.applyAdjustmentsToRegion(addCounters(BC.BreakCount, BC.ContinueCount));
830 }
831
832 void VisitObjCForCollectionStmt(const ObjCForCollectionStmt *S) {
833 mapSourceCodeRange(S->getLocStart());
834 Visit(S->getElement());
835 // Counter tracks the body of the loop.
836 RegionMapper Cnt(this, S);
837 BreakContinueStack.push_back(BreakContinue());
Alex Lorenzfdd769e2014-08-20 17:11:53 +0000838 Cnt.beginRegion();
Alex Lorenzee024992014-08-04 18:41:51 +0000839 VisitSubStmtRBraceState(S->getBody());
840 BreakContinue BC = BreakContinueStack.pop_back_val();
841 Cnt.adjustForControlFlow();
842 Cnt.applyAdjustmentsToRegion(addCounters(BC.BreakCount, BC.ContinueCount));
843 }
844
845 void VisitSwitchStmt(const SwitchStmt *S) {
846 mapSourceCodeRange(S->getLocStart());
847 Visit(S->getCond());
848 BreakContinueStack.push_back(BreakContinue());
849 // Map the '}' for the body to have the same count as the regions after
850 // the switch.
851 SourceLocation RBracLoc;
852 if (const auto *CS = dyn_cast<CompoundStmt>(S->getBody())) {
853 mapSourceCodeRange(CS->getLBracLoc());
854 setCurrentRegionUnreachable(S);
855 for (Stmt::const_child_range I = CS->children(); I; ++I) {
856 if (*I)
857 this->Visit(*I);
858 }
859 RBracLoc = CS->getRBracLoc();
860 } else {
861 setCurrentRegionUnreachable(S);
862 Visit(S->getBody());
863 }
864 // If the switch is inside a loop, add the continue counts.
865 BreakContinue BC = BreakContinueStack.pop_back_val();
866 if (!BreakContinueStack.empty())
867 BreakContinueStack.back().ContinueCount = addCounters(
868 BreakContinueStack.back().ContinueCount, BC.ContinueCount);
869 // Counter tracks the exit block of the switch.
870 RegionMapper ExitCnt(this, S);
871 ExitCnt.beginRegion();
872 if (RBracLoc.isValid())
873 mapSourceCodeRange(RBracLoc);
874 }
875
876 void VisitCaseStmt(const CaseStmt *S) {
877 // Counter for this particular case. This counts only jumps from the
878 // switch header and does not include fallthrough from the case before
879 // this one.
880 RegionMapper Cnt(this, S);
881 Cnt.beginRegion(/*AddIncomingFallThrough=*/true);
882 mapSourceCodeRange(S->getLocStart());
883 mapToken(S->getColonLoc());
884 Visit(S->getSubStmt());
885 }
886
887 void VisitDefaultStmt(const DefaultStmt *S) {
888 // Counter for this default case. This does not include fallthrough from
889 // the previous case.
890 RegionMapper Cnt(this, S);
891 Cnt.beginRegion(/*AddIncomingFallThrough=*/true);
892 mapSourceCodeRange(S->getLocStart());
893 mapToken(S->getColonLoc());
894 Visit(S->getSubStmt());
895 }
896
897 void VisitIfStmt(const IfStmt *S) {
898 mapSourceCodeRange(S->getLocStart());
899 Visit(S->getCond());
900 mapToken(S->getElseLoc());
901
902 // Counter tracks the "then" part of an if statement. The count for
903 // the "else" part, if it exists, will be calculated from this counter.
904 RegionMapper Cnt(this, S);
905 Cnt.beginRegion();
906 VisitSubStmtRBraceState(S->getThen());
907 Cnt.adjustForControlFlow();
908
909 if (S->getElse()) {
910 Cnt.beginElseRegion();
911 VisitSubStmtRBraceState(S->getElse());
912 Cnt.adjustForControlFlow();
913 }
914 Cnt.applyAdjustmentsToRegion();
915 }
916
917 void VisitCXXTryStmt(const CXXTryStmt *S) {
918 mapSourceCodeRange(S->getLocStart());
919 Visit(S->getTryBlock());
920 for (unsigned I = 0, E = S->getNumHandlers(); I < E; ++I)
921 Visit(S->getHandler(I));
922 // Counter tracks the continuation block of the try statement.
923 RegionMapper Cnt(this, S);
924 Cnt.beginRegion();
925 }
926
927 void VisitCXXCatchStmt(const CXXCatchStmt *S) {
928 mapSourceCodeRange(S->getLocStart());
929 // Counter tracks the catch statement's handler block.
930 RegionMapper Cnt(this, S);
931 Cnt.beginRegion();
932 VisitSubStmtRBraceState(S->getHandlerBlock());
933 }
934
935 void VisitAbstractConditionalOperator(const AbstractConditionalOperator *E) {
936 Visit(E->getCond());
937 mapToken(E->getQuestionLoc());
938 auto State = getCurrentState();
939
940 // Counter tracks the "true" part of a conditional operator. The
941 // count in the "false" part will be calculated from this counter.
942 RegionMapper Cnt(this, E);
943 Cnt.beginRegion();
944 Visit(E->getTrueExpr());
945 Cnt.adjustForControlFlow();
946
947 mapToken(State, E->getColonLoc());
948
949 Cnt.beginElseRegion();
950 Visit(E->getFalseExpr());
951 Cnt.adjustForControlFlow();
952
953 Cnt.applyAdjustmentsToRegion();
954 }
955
956 void VisitBinLAnd(const BinaryOperator *E) {
957 Visit(E->getLHS());
958 mapToken(E->getOperatorLoc());
959 // Counter tracks the right hand side of a logical and operator.
960 RegionMapper Cnt(this, E);
961 Cnt.beginRegion();
962 Visit(E->getRHS());
963 Cnt.adjustForControlFlow();
964 Cnt.applyAdjustmentsToRegion();
965 }
966
967 void VisitBinLOr(const BinaryOperator *E) {
968 Visit(E->getLHS());
969 mapToken(E->getOperatorLoc());
970 // Counter tracks the right hand side of a logical or operator.
971 RegionMapper Cnt(this, E);
972 Cnt.beginRegion();
973 Visit(E->getRHS());
974 Cnt.adjustForControlFlow();
975 Cnt.applyAdjustmentsToRegion();
976 }
977
978 void VisitParenExpr(const ParenExpr *E) {
979 mapToken(E->getLParen());
980 Visit(E->getSubExpr());
981 mapToken(E->getRParen());
982 }
983
984 void VisitBinaryOperator(const BinaryOperator *E) {
985 Visit(E->getLHS());
986 mapToken(E->getOperatorLoc());
987 Visit(E->getRHS());
988 }
989
990 void VisitUnaryOperator(const UnaryOperator *E) {
991 bool Postfix = E->isPostfix();
992 if (!Postfix)
993 mapToken(E->getOperatorLoc());
994 Visit(E->getSubExpr());
995 if (Postfix)
996 mapToken(E->getOperatorLoc());
997 }
998
999 void VisitMemberExpr(const MemberExpr *E) {
1000 Visit(E->getBase());
1001 mapToken(E->getMemberLoc());
1002 }
1003
1004 void VisitCallExpr(const CallExpr *E) {
1005 Visit(E->getCallee());
1006 for (const auto &Arg : E->arguments())
1007 Visit(Arg);
1008 mapToken(E->getRParenLoc());
1009 }
1010
1011 void VisitArraySubscriptExpr(const ArraySubscriptExpr *E) {
1012 Visit(E->getLHS());
1013 Visit(E->getRHS());
1014 mapToken(E->getRBracketLoc());
1015 }
1016
1017 void VisitCStyleCastExpr(const CStyleCastExpr *E) {
1018 mapToken(E->getLParenLoc());
1019 mapToken(E->getRParenLoc());
1020 Visit(E->getSubExpr());
1021 }
1022
1023 // Map literals as tokens so that the macros like #define PI 3.14
1024 // won't generate coverage mapping regions.
1025
1026 void VisitIntegerLiteral(const IntegerLiteral *E) {
1027 mapToken(E->getLocStart());
1028 }
1029
1030 void VisitFloatingLiteral(const FloatingLiteral *E) {
1031 mapToken(E->getLocStart());
1032 }
1033
1034 void VisitCharacterLiteral(const CharacterLiteral *E) {
1035 mapToken(E->getLocStart());
1036 }
1037
1038 void VisitStringLiteral(const StringLiteral *E) {
1039 mapToken(E->getLocStart());
1040 }
1041
1042 void VisitImaginaryLiteral(const ImaginaryLiteral *E) {
1043 mapToken(E->getLocStart());
1044 }
Alex Lorenz01a0d062014-08-20 17:10:56 +00001045
1046 void VisitObjCMessageExpr(const ObjCMessageExpr *E) {
1047 mapToken(E->getLeftLoc());
1048 for (Stmt::const_child_range I = static_cast<const Stmt*>(E)->children(); I;
1049 ++I) {
1050 if (*I)
1051 this->Visit(*I);
1052 }
1053 mapToken(E->getRightLoc());
1054 }
Alex Lorenzee024992014-08-04 18:41:51 +00001055};
1056}
1057
1058static bool isMachO(const CodeGenModule &CGM) {
1059 return CGM.getTarget().getTriple().isOSBinFormatMachO();
1060}
1061
1062static StringRef getCoverageSection(const CodeGenModule &CGM) {
1063 return isMachO(CGM) ? "__DATA,__llvm_covmap" : "__llvm_covmap";
1064}
1065
Alex Lorenzf2cf38e2014-08-08 23:41:24 +00001066static void dump(llvm::raw_ostream &OS, const CoverageMappingRecord &Function) {
1067 OS << Function.FunctionName << ":\n";
1068 CounterMappingContext Ctx(Function.Expressions);
1069 for (const auto &R : Function.MappingRegions) {
1070 OS.indent(2);
1071 switch (R.Kind) {
1072 case CounterMappingRegion::CodeRegion:
1073 break;
1074 case CounterMappingRegion::ExpansionRegion:
1075 OS << "Expansion,";
1076 break;
1077 case CounterMappingRegion::SkippedRegion:
1078 OS << "Skipped,";
1079 break;
1080 }
1081
1082 OS << "File " << R.FileID << ", " << R.LineStart << ":"
1083 << R.ColumnStart << " -> " << R.LineEnd << ":" << R.ColumnEnd
1084 << " = ";
1085 Ctx.dump(R.Count);
1086 OS << " (HasCodeBefore = " << R.HasCodeBefore;
1087 if (R.Kind == CounterMappingRegion::ExpansionRegion)
1088 OS << ", Expanded file = " << R.ExpandedFileID;
1089
1090 OS << ")\n";
1091 }
1092}
1093
Alex Lorenzee024992014-08-04 18:41:51 +00001094void CoverageMappingModuleGen::addFunctionMappingRecord(
Alex Lorenzf2cf38e2014-08-08 23:41:24 +00001095 llvm::GlobalVariable *FunctionName, StringRef FunctionNameValue,
Alex Lorenz1d45c5b2014-08-21 19:25:27 +00001096 uint64_t FunctionHash, const std::string &CoverageMapping) {
Alex Lorenzee024992014-08-04 18:41:51 +00001097 llvm::LLVMContext &Ctx = CGM.getLLVMContext();
1098 auto *Int32Ty = llvm::Type::getInt32Ty(Ctx);
Alex Lorenz1d45c5b2014-08-21 19:25:27 +00001099 auto *Int64Ty = llvm::Type::getInt64Ty(Ctx);
Alex Lorenzee024992014-08-04 18:41:51 +00001100 auto *Int8PtrTy = llvm::Type::getInt8PtrTy(Ctx);
1101 if (!FunctionRecordTy) {
Alex Lorenz1d45c5b2014-08-21 19:25:27 +00001102 llvm::Type *FunctionRecordTypes[] = {Int8PtrTy, Int32Ty, Int32Ty, Int64Ty};
Alex Lorenzee024992014-08-04 18:41:51 +00001103 FunctionRecordTy =
1104 llvm::StructType::get(Ctx, makeArrayRef(FunctionRecordTypes));
1105 }
1106
1107 llvm::Constant *FunctionRecordVals[] = {
1108 llvm::ConstantExpr::getBitCast(FunctionName, Int8PtrTy),
Alex Lorenzf2cf38e2014-08-08 23:41:24 +00001109 llvm::ConstantInt::get(Int32Ty, FunctionNameValue.size()),
Alex Lorenz1d45c5b2014-08-21 19:25:27 +00001110 llvm::ConstantInt::get(Int32Ty, CoverageMapping.size()),
1111 llvm::ConstantInt::get(Int64Ty, FunctionHash)};
Alex Lorenzee024992014-08-04 18:41:51 +00001112 FunctionRecords.push_back(llvm::ConstantStruct::get(
1113 FunctionRecordTy, makeArrayRef(FunctionRecordVals)));
1114 CoverageMappings += CoverageMapping;
Alex Lorenzf2cf38e2014-08-08 23:41:24 +00001115
1116 if (CGM.getCodeGenOpts().DumpCoverageMapping) {
1117 // Dump the coverage mapping data for this function by decoding the
1118 // encoded data. This allows us to dump the mapping regions which were
1119 // also processed by the CoverageMappingWriter which performs
1120 // additional minimization operations such as reducing the number of
1121 // expressions.
1122 std::vector<StringRef> Filenames;
1123 std::vector<CounterExpression> Expressions;
1124 std::vector<CounterMappingRegion> Regions;
1125 llvm::SmallVector<StringRef, 16> FilenameRefs;
1126 FilenameRefs.resize(FileEntries.size());
1127 for (const auto &Entry : FileEntries)
1128 FilenameRefs[Entry.second] = Entry.first->getName();
1129 RawCoverageMappingReader Reader(FunctionNameValue, CoverageMapping,
1130 FilenameRefs,
1131 Filenames, Expressions, Regions);
1132 CoverageMappingRecord FunctionRecord;
1133 if (Reader.read(FunctionRecord))
1134 return;
1135 dump(llvm::outs(), FunctionRecord);
1136 }
Alex Lorenzee024992014-08-04 18:41:51 +00001137}
1138
1139void CoverageMappingModuleGen::emit() {
1140 if (FunctionRecords.empty())
1141 return;
1142 llvm::LLVMContext &Ctx = CGM.getLLVMContext();
1143 auto *Int32Ty = llvm::Type::getInt32Ty(Ctx);
1144
1145 // Create the filenames and merge them with coverage mappings
1146 llvm::SmallVector<std::string, 16> FilenameStrs;
1147 llvm::SmallVector<StringRef, 16> FilenameRefs;
1148 FilenameStrs.resize(FileEntries.size());
1149 FilenameRefs.resize(FileEntries.size());
1150 for (const auto &Entry : FileEntries) {
1151 llvm::SmallString<256> Path(Entry.first->getName());
1152 llvm::sys::fs::make_absolute(Path);
1153
1154 auto I = Entry.second;
1155 FilenameStrs[I] = std::move(std::string(Path.begin(), Path.end()));
1156 FilenameRefs[I] = FilenameStrs[I];
1157 }
1158
1159 std::string FilenamesAndCoverageMappings;
1160 llvm::raw_string_ostream OS(FilenamesAndCoverageMappings);
1161 CoverageFilenamesSectionWriter(FilenameRefs).write(OS);
1162 OS << CoverageMappings;
1163 size_t CoverageMappingSize = CoverageMappings.size();
1164 size_t FilenamesSize = OS.str().size() - CoverageMappingSize;
1165 // Append extra zeroes if necessary to ensure that the size of the filenames
1166 // and coverage mappings is a multiple of 8.
1167 if (size_t Rem = OS.str().size() % 8) {
1168 CoverageMappingSize += 8 - Rem;
1169 for (size_t I = 0, S = 8 - Rem; I < S; ++I)
1170 OS << '\0';
1171 }
1172 auto *FilenamesAndMappingsVal =
1173 llvm::ConstantDataArray::getString(Ctx, OS.str(), false);
1174
1175 // Create the deferred function records array
1176 auto RecordsTy =
1177 llvm::ArrayType::get(FunctionRecordTy, FunctionRecords.size());
1178 auto RecordsVal = llvm::ConstantArray::get(RecordsTy, FunctionRecords);
1179
1180 // Create the coverage data record
1181 llvm::Type *CovDataTypes[] = {Int32Ty, Int32Ty,
1182 Int32Ty, Int32Ty,
1183 RecordsTy, FilenamesAndMappingsVal->getType()};
1184 auto CovDataTy = llvm::StructType::get(Ctx, makeArrayRef(CovDataTypes));
1185 llvm::Constant *TUDataVals[] = {
1186 llvm::ConstantInt::get(Int32Ty, FunctionRecords.size()),
1187 llvm::ConstantInt::get(Int32Ty, FilenamesSize),
1188 llvm::ConstantInt::get(Int32Ty, CoverageMappingSize),
1189 llvm::ConstantInt::get(Int32Ty,
1190 /*Version=*/CoverageMappingVersion1),
1191 RecordsVal, FilenamesAndMappingsVal};
1192 auto CovDataVal =
1193 llvm::ConstantStruct::get(CovDataTy, makeArrayRef(TUDataVals));
1194 auto CovData = new llvm::GlobalVariable(CGM.getModule(), CovDataTy, true,
1195 llvm::GlobalValue::InternalLinkage,
1196 CovDataVal,
1197 "__llvm_coverage_mapping");
1198
1199 CovData->setSection(getCoverageSection(CGM));
1200 CovData->setAlignment(8);
1201
1202 // Make sure the data doesn't get deleted.
1203 CGM.addUsedGlobal(CovData);
1204}
1205
1206unsigned CoverageMappingModuleGen::getFileID(const FileEntry *File) {
1207 auto It = FileEntries.find(File);
1208 if (It != FileEntries.end())
1209 return It->second;
1210 unsigned FileID = FileEntries.size();
1211 FileEntries.insert(std::make_pair(File, FileID));
1212 return FileID;
1213}
1214
1215void CoverageMappingGen::emitCounterMapping(const Decl *D,
1216 llvm::raw_ostream &OS) {
1217 assert(CounterMap);
1218 CounterCoverageMappingBuilder Walker(CVM, *CounterMap, NumRegionCounters, SM,
1219 LangOpts);
1220 Walker.VisitDecl(D);
1221 Walker.write(OS);
1222}
1223
1224void CoverageMappingGen::emitEmptyMapping(const Decl *D,
1225 llvm::raw_ostream &OS) {
1226 EmptyCoverageMappingBuilder Walker(CVM, SM, LangOpts);
1227 Walker.VisitDecl(D);
1228 Walker.write(OS);
1229}