Coverage Report

Created: 2022-05-17 06:19

/Users/buildslave/jenkins/workspace/coverage/llvm-project/clang/include/clang/Analysis/FlowSensitive/StorageLocation.h
Line
Count
Source (jump to first uncovered line)
1
//===-- StorageLocation.h ---------------------------------------*- C++ -*-===//
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
//
9
// This file defines classes that represent elements of the local variable store
10
// and of the heap during dataflow analysis.
11
//
12
//===----------------------------------------------------------------------===//
13
14
#ifndef LLVM_CLANG_ANALYSIS_FLOWSENSITIVE_STORAGELOCATION_H
15
#define LLVM_CLANG_ANALYSIS_FLOWSENSITIVE_STORAGELOCATION_H
16
17
#include "clang/AST/Decl.h"
18
#include "clang/AST/Type.h"
19
#include "llvm/ADT/DenseMap.h"
20
21
namespace clang {
22
namespace dataflow {
23
24
/// Base class for elements of the local variable store and of the heap.
25
///
26
/// Each storage location holds a value. The mapping from storage locations to
27
/// values is stored in the environment.
28
class StorageLocation {
29
public:
30
  enum class Kind { Scalar, Aggregate };
31
32
1.66k
  StorageLocation(Kind LocKind, QualType Type) : LocKind(LocKind), Type(Type) {}
33
34
1.66k
  virtual ~StorageLocation() = default;
35
36
60
  Kind getKind() const { return LocKind; }
37
38
1.42k
  QualType getType() const { return Type; }
39
40
private:
41
  Kind LocKind;
42
  QualType Type;
43
};
44
45
/// A storage location that is not subdivided further for the purposes of
46
/// abstract interpretation. For example: `int`, `int*`, `int&`.
47
class ScalarStorageLocation final : public StorageLocation {
48
public:
49
  explicit ScalarStorageLocation(QualType Type)
50
799
      : StorageLocation(Kind::Scalar, Type) {}
51
52
  static bool classof(const StorageLocation *Loc) {
53
    return Loc->getKind() == Kind::Scalar;
54
  }
55
};
56
57
/// A storage location which is subdivided into smaller storage locations that
58
/// can be traced independently by abstract interpretation. For example: a
59
/// struct with public members. The child map is flat, so when used for a struct
60
/// or class type, all accessible members of base struct and class types are
61
/// directly accesible as children of this location.
62
class AggregateStorageLocation final : public StorageLocation {
63
public:
64
  explicit AggregateStorageLocation(QualType Type)
65
      : AggregateStorageLocation(
66
0
            Type, llvm::DenseMap<const ValueDecl *, StorageLocation *>()) {}
67
68
  AggregateStorageLocation(
69
      QualType Type,
70
      llvm::DenseMap<const ValueDecl *, StorageLocation *> Children)
71
864
      : StorageLocation(Kind::Aggregate, Type), Children(std::move(Children)) {}
72
73
47
  static bool classof(const StorageLocation *Loc) {
74
47
    return Loc->getKind() == Kind::Aggregate;
75
47
  }
76
77
  /// Returns the child storage location for `D`.
78
241
  StorageLocation &getChild(const ValueDecl &D) const {
79
241
    auto It = Children.find(&D);
80
241
    assert(It != Children.end());
81
0
    return *It->second;
82
241
  }
83
84
private:
85
  llvm::DenseMap<const ValueDecl *, StorageLocation *> Children;
86
};
87
88
} // namespace dataflow
89
} // namespace clang
90
91
#endif // LLVM_CLANG_ANALYSIS_FLOWSENSITIVE_STORAGELOCATION_H