Coverage Report

Created: 2021-08-24 07:12

/Users/buildslave/jenkins/workspace/coverage/llvm-project/clang/lib/Frontend/TestModuleFileExtension.cpp
Line
Count
Source (jump to first uncovered line)
1
//===-- TestModuleFileExtension.cpp - Module Extension Tester -------------===//
2
//
3
// Part of the LLVM Project, under the Apache License v2.0 with LLVM Exceptions.
4
// See https://llvm.org/LICENSE.txt for license information.
5
// SPDX-License-Identifier: Apache-2.0 WITH LLVM-exception
6
//
7
//===----------------------------------------------------------------------===//
8
#include "TestModuleFileExtension.h"
9
#include "clang/Frontend/FrontendDiagnostic.h"
10
#include "clang/Serialization/ASTReader.h"
11
#include "llvm/ADT/Hashing.h"
12
#include "llvm/Bitstream/BitstreamWriter.h"
13
#include "llvm/Support/raw_ostream.h"
14
#include <cstdio>
15
using namespace clang;
16
using namespace clang::serialization;
17
18
char TestModuleFileExtension::ID = 0;
19
20
12
TestModuleFileExtension::Writer::~Writer() { }
21
22
void TestModuleFileExtension::Writer::writeExtensionContents(
23
       Sema &SemaRef,
24
12
       llvm::BitstreamWriter &Stream) {
25
12
  using namespace llvm;
26
27
  // Write an abbreviation for this record.
28
12
  auto Abv = std::make_shared<llvm::BitCodeAbbrev>();
29
12
  Abv->Add(BitCodeAbbrevOp(FIRST_EXTENSION_RECORD_ID));
30
12
  Abv->Add(BitCodeAbbrevOp(BitCodeAbbrevOp::VBR, 6)); // # of characters
31
12
  Abv->Add(BitCodeAbbrevOp(BitCodeAbbrevOp::Blob));   // message
32
12
  auto Abbrev = Stream.EmitAbbrev(std::move(Abv));
33
34
  // Write a message into the extension block.
35
12
  SmallString<64> Message;
36
12
  {
37
12
    auto Ext = static_cast<TestModuleFileExtension *>(getExtension());
38
12
    raw_svector_ostream OS(Message);
39
12
    OS << "Hello from " << Ext->BlockName << " v" << Ext->MajorVersion << "."
40
12
       << Ext->MinorVersion;
41
12
  }
42
12
  uint64_t Record[] = {FIRST_EXTENSION_RECORD_ID, Message.size()};
43
12
  Stream.EmitRecordWithBlob(Abbrev, Record, Message);
44
12
}
45
46
TestModuleFileExtension::Reader::Reader(ModuleFileExtension *Ext,
47
                                        const llvm::BitstreamCursor &InStream)
48
  : ModuleFileExtensionReader(Ext), Stream(InStream)
49
13
{
50
  // Read the extension block.
51
13
  SmallVector<uint64_t, 4> Record;
52
26
  while (true) {
53
26
    llvm::Expected<llvm::BitstreamEntry> MaybeEntry =
54
26
        Stream.advanceSkippingSubblocks();
55
26
    if (!MaybeEntry)
56
0
      (void)MaybeEntry.takeError();
57
26
    llvm::BitstreamEntry Entry = MaybeEntry.get();
58
59
26
    switch (Entry.Kind) {
60
0
    case llvm::BitstreamEntry::SubBlock:
61
13
    case llvm::BitstreamEntry::EndBlock:
62
13
    case llvm::BitstreamEntry::Error:
63
13
      return;
64
65
13
    case llvm::BitstreamEntry::Record:
66
13
      break;
67
26
    }
68
69
13
    Record.clear();
70
13
    StringRef Blob;
71
13
    Expected<unsigned> MaybeRecCode =
72
13
        Stream.readRecord(Entry.ID, Record, &Blob);
73
13
    if (!MaybeRecCode)
74
0
      fprintf(stderr, "Failed reading rec code: %s\n",
75
0
              toString(MaybeRecCode.takeError()).c_str());
76
13
    switch (MaybeRecCode.get()) {
77
13
    case FIRST_EXTENSION_RECORD_ID: {
78
13
      StringRef Message = Blob.substr(0, Record[0]);
79
13
      fprintf(stderr, "Read extension block message: %s\n",
80
13
              Message.str().c_str());
81
13
      break;
82
0
    }
83
13
    }
84
13
  }
85
13
}
86
87
13
TestModuleFileExtension::Reader::~Reader() { }
88
89
36
TestModuleFileExtension::~TestModuleFileExtension() { }
90
91
ModuleFileExtensionMetadata
92
40
TestModuleFileExtension::getExtensionMetadata() const {
93
40
  return { BlockName, MajorVersion, MinorVersion, UserInfo };
94
40
}
95
96
llvm::hash_code TestModuleFileExtension::hashExtension(
97
52
                  llvm::hash_code Code) const {
98
52
  if (Hashed) {
99
16
    Code = llvm::hash_combine(Code, BlockName);
100
16
    Code = llvm::hash_combine(Code, MajorVersion);
101
16
    Code = llvm::hash_combine(Code, MinorVersion);
102
16
    Code = llvm::hash_combine(Code, UserInfo);
103
16
  }
104
105
52
  return Code;
106
52
}
107
108
std::unique_ptr<ModuleFileExtensionWriter>
109
12
TestModuleFileExtension::createExtensionWriter(ASTWriter &) {
110
12
  return std::unique_ptr<ModuleFileExtensionWriter>(new Writer(this));
111
12
}
112
113
std::unique_ptr<ModuleFileExtensionReader>
114
TestModuleFileExtension::createExtensionReader(
115
  const ModuleFileExtensionMetadata &Metadata,
116
  ASTReader &Reader, serialization::ModuleFile &Mod,
117
  const llvm::BitstreamCursor &Stream)
118
15
{
119
15
  assert(Metadata.BlockName == BlockName && "Wrong block name");
120
15
  if (std::make_pair(Metadata.MajorVersion, Metadata.MinorVersion) !=
121
15
        std::make_pair(MajorVersion, MinorVersion)) {
122
2
    Reader.getDiags().Report(Mod.ImportLoc,
123
2
                             diag::err_test_module_file_extension_version)
124
2
      << BlockName << Metadata.MajorVersion << Metadata.MinorVersion
125
2
      << MajorVersion << MinorVersion;
126
2
    return nullptr;
127
2
  }
128
129
13
  return std::unique_ptr<ModuleFileExtensionReader>(
130
13
                                                    new TestModuleFileExtension::Reader(this, Stream));
131
15
}
132
133
38
std::string TestModuleFileExtension::str() const {
134
38
  std::string Buffer;
135
38
  llvm::raw_string_ostream OS(Buffer);
136
38
  OS << BlockName << ":" << MajorVersion << ":" << MinorVersion << ":" << Hashed
137
38
     << ":" << UserInfo;
138
38
  return OS.str();
139
38
}