1//===- GlobalStatus.h - Compute status info for globals ---------*- 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#ifndef LLVM_TRANSFORMS_UTILS_GLOBALSTATUS_H
10#define LLVM_TRANSFORMS_UTILS_GLOBALSTATUS_H
11
12#include "llvm/IR/Instructions.h"
13#include "llvm/Support/AtomicOrdering.h"
14
15namespace llvm {
16
17class Constant;
18class Function;
19class Value;
20
21/// It is safe to destroy a constant iff it is only used by constants itself.
22/// Note that constants cannot be cyclic, so this test is pretty easy to
23/// implement recursively.
24///
25bool isSafeToDestroyConstant(const Constant *C);
26
27/// As we analyze each global, keep track of some information about it. If we
28/// find out that the address of the global is taken, none of this info will be
29/// accurate.
30struct GlobalStatus {
31 /// True if the global's address is used in a comparison.
32 bool IsCompared = false;
33
34 /// True if the global is ever loaded. If the global isn't ever loaded it
35 /// can be deleted.
36 bool IsLoaded = false;
37
38 /// Number of stores to the global.
39 unsigned NumStores = 0;
40
41 /// Keep track of what stores to the global look like.
42 enum StoredType {
43 /// There is no store to this global. It can thus be marked constant.
44 NotStored,
45
46 /// This global is stored to, but the only thing stored is the constant it
47 /// was initialized with. This is only tracked for scalar globals.
48 InitializerStored,
49
50 /// This global is stored to, but only its initializer and one other value
51 /// is ever stored to it. If this global isStoredOnce, we track the value
52 /// stored to it via StoredOnceStore below. This is only tracked for scalar
53 /// globals.
54 StoredOnce,
55
56 /// This global is stored to by multiple values or something else that we
57 /// cannot track.
58 Stored
59 } StoredType = NotStored;
60
61 /// If only one value (besides the initializer constant) is ever stored to
62 /// this global, keep track of what value it is via the store instruction.
63 const StoreInst *StoredOnceStore = nullptr;
64
65 /// If only one value (besides the initializer constant) is ever stored to
66 /// this global return the stored value.
67 Value *getStoredOnceValue() const {
68 return (StoredType == StoredOnce && StoredOnceStore)
69 ? StoredOnceStore->getOperand(i_nocapture: 0)
70 : nullptr;
71 }
72
73 /// These start out null/false. When the first accessing function is noticed,
74 /// it is recorded. When a second different accessing function is noticed,
75 /// HasMultipleAccessingFunctions is set to true.
76 const Function *AccessingFunction = nullptr;
77 bool HasMultipleAccessingFunctions = false;
78
79 /// Set to the strongest atomic ordering requirement.
80 AtomicOrdering Ordering = AtomicOrdering::NotAtomic;
81
82 GlobalStatus();
83
84 /// Look at all uses of the global and fill in the GlobalStatus structure. If
85 /// the global has its address taken, return true to indicate we can't do
86 /// anything with it.
87 static bool analyzeGlobal(const Value *V, GlobalStatus &GS);
88};
89
90} // end namespace llvm
91
92#endif // LLVM_TRANSFORMS_UTILS_GLOBALSTATUS_H
93

source code of llvm/include/llvm/Transforms/Utils/GlobalStatus.h