1*9e3b08aeSAndroid Build Coastguard Worker // SPDX-License-Identifier: Apache-2.0 WITH LLVM-exception
2*9e3b08aeSAndroid Build Coastguard Worker // -*- mode: C++ -*-
3*9e3b08aeSAndroid Build Coastguard Worker //
4*9e3b08aeSAndroid Build Coastguard Worker // Copyright 2020-2022 Google LLC
5*9e3b08aeSAndroid Build Coastguard Worker //
6*9e3b08aeSAndroid Build Coastguard Worker // Licensed under the Apache License v2.0 with LLVM Exceptions (the
7*9e3b08aeSAndroid Build Coastguard Worker // "License"); you may not use this file except in compliance with the
8*9e3b08aeSAndroid Build Coastguard Worker // License. You may obtain a copy of the License at
9*9e3b08aeSAndroid Build Coastguard Worker //
10*9e3b08aeSAndroid Build Coastguard Worker // https://llvm.org/LICENSE.txt
11*9e3b08aeSAndroid Build Coastguard Worker //
12*9e3b08aeSAndroid Build Coastguard Worker // Unless required by applicable law or agreed to in writing, software
13*9e3b08aeSAndroid Build Coastguard Worker // distributed under the License is distributed on an "AS IS" BASIS,
14*9e3b08aeSAndroid Build Coastguard Worker // WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
15*9e3b08aeSAndroid Build Coastguard Worker // See the License for the specific language governing permissions and
16*9e3b08aeSAndroid Build Coastguard Worker // limitations under the License.
17*9e3b08aeSAndroid Build Coastguard Worker //
18*9e3b08aeSAndroid Build Coastguard Worker // Author: Maria Teguiani
19*9e3b08aeSAndroid Build Coastguard Worker // Author: Giuliano Procida
20*9e3b08aeSAndroid Build Coastguard Worker // Author: Ignes Simeonova
21*9e3b08aeSAndroid Build Coastguard Worker
22*9e3b08aeSAndroid Build Coastguard Worker #include "graph.h"
23*9e3b08aeSAndroid Build Coastguard Worker
24*9e3b08aeSAndroid Build Coastguard Worker #include <limits>
25*9e3b08aeSAndroid Build Coastguard Worker #include <ostream>
26*9e3b08aeSAndroid Build Coastguard Worker #include <string>
27*9e3b08aeSAndroid Build Coastguard Worker #include <string_view>
28*9e3b08aeSAndroid Build Coastguard Worker
29*9e3b08aeSAndroid Build Coastguard Worker #include "hex.h"
30*9e3b08aeSAndroid Build Coastguard Worker
31*9e3b08aeSAndroid Build Coastguard Worker namespace stg {
32*9e3b08aeSAndroid Build Coastguard Worker
33*9e3b08aeSAndroid Build Coastguard Worker const Id Id::kInvalid(std::numeric_limits<decltype(Id::ix_)>::max());
34*9e3b08aeSAndroid Build Coastguard Worker
operator <<(std::ostream & os,Id id)35*9e3b08aeSAndroid Build Coastguard Worker std::ostream& operator<<(std::ostream& os, Id id) {
36*9e3b08aeSAndroid Build Coastguard Worker return os << '<' << id.ix_ << '>';
37*9e3b08aeSAndroid Build Coastguard Worker }
38*9e3b08aeSAndroid Build Coastguard Worker
operator <<(std::ostream & os,BaseClass::Inheritance inheritance)39*9e3b08aeSAndroid Build Coastguard Worker std::ostream& operator<<(std::ostream& os, BaseClass::Inheritance inheritance) {
40*9e3b08aeSAndroid Build Coastguard Worker switch (inheritance) {
41*9e3b08aeSAndroid Build Coastguard Worker case BaseClass::Inheritance::NON_VIRTUAL:
42*9e3b08aeSAndroid Build Coastguard Worker return os << "non-virtual";
43*9e3b08aeSAndroid Build Coastguard Worker case BaseClass::Inheritance::VIRTUAL:
44*9e3b08aeSAndroid Build Coastguard Worker return os << "virtual";
45*9e3b08aeSAndroid Build Coastguard Worker }
46*9e3b08aeSAndroid Build Coastguard Worker }
47*9e3b08aeSAndroid Build Coastguard Worker
48*9e3b08aeSAndroid Build Coastguard Worker namespace {
49*9e3b08aeSAndroid Build Coastguard Worker
ToString(StructUnion::Kind kind)50*9e3b08aeSAndroid Build Coastguard Worker std::string_view ToString(StructUnion::Kind kind) {
51*9e3b08aeSAndroid Build Coastguard Worker switch (kind) {
52*9e3b08aeSAndroid Build Coastguard Worker case StructUnion::Kind::STRUCT:
53*9e3b08aeSAndroid Build Coastguard Worker return "struct";
54*9e3b08aeSAndroid Build Coastguard Worker case StructUnion::Kind::UNION:
55*9e3b08aeSAndroid Build Coastguard Worker return "union";
56*9e3b08aeSAndroid Build Coastguard Worker }
57*9e3b08aeSAndroid Build Coastguard Worker }
58*9e3b08aeSAndroid Build Coastguard Worker
59*9e3b08aeSAndroid Build Coastguard Worker } // namespace
60*9e3b08aeSAndroid Build Coastguard Worker
operator <<(std::ostream & os,StructUnion::Kind kind)61*9e3b08aeSAndroid Build Coastguard Worker std::ostream& operator<<(std::ostream& os, StructUnion::Kind kind) {
62*9e3b08aeSAndroid Build Coastguard Worker return os << ToString(kind);
63*9e3b08aeSAndroid Build Coastguard Worker }
64*9e3b08aeSAndroid Build Coastguard Worker
operator +=(std::string & os,StructUnion::Kind kind)65*9e3b08aeSAndroid Build Coastguard Worker std::string& operator+=(std::string& os, StructUnion::Kind kind) {
66*9e3b08aeSAndroid Build Coastguard Worker return os += ToString(kind);
67*9e3b08aeSAndroid Build Coastguard Worker }
68*9e3b08aeSAndroid Build Coastguard Worker
operator <<(std::ostream & os,Qualifier qualifier)69*9e3b08aeSAndroid Build Coastguard Worker std::ostream& operator<<(std::ostream& os, Qualifier qualifier) {
70*9e3b08aeSAndroid Build Coastguard Worker switch (qualifier) {
71*9e3b08aeSAndroid Build Coastguard Worker case Qualifier::CONST:
72*9e3b08aeSAndroid Build Coastguard Worker return os << "const";
73*9e3b08aeSAndroid Build Coastguard Worker case Qualifier::VOLATILE:
74*9e3b08aeSAndroid Build Coastguard Worker return os << "volatile";
75*9e3b08aeSAndroid Build Coastguard Worker case Qualifier::RESTRICT:
76*9e3b08aeSAndroid Build Coastguard Worker return os << "restrict";
77*9e3b08aeSAndroid Build Coastguard Worker case Qualifier::ATOMIC:
78*9e3b08aeSAndroid Build Coastguard Worker return os << "atomic";
79*9e3b08aeSAndroid Build Coastguard Worker }
80*9e3b08aeSAndroid Build Coastguard Worker }
81*9e3b08aeSAndroid Build Coastguard Worker
operator <<(std::ostream & os,ElfSymbol::SymbolType type)82*9e3b08aeSAndroid Build Coastguard Worker std::ostream& operator<<(std::ostream& os, ElfSymbol::SymbolType type) {
83*9e3b08aeSAndroid Build Coastguard Worker switch (type) {
84*9e3b08aeSAndroid Build Coastguard Worker case ElfSymbol::SymbolType::NOTYPE:
85*9e3b08aeSAndroid Build Coastguard Worker return os << "no-type";
86*9e3b08aeSAndroid Build Coastguard Worker case ElfSymbol::SymbolType::OBJECT:
87*9e3b08aeSAndroid Build Coastguard Worker return os << "variable";
88*9e3b08aeSAndroid Build Coastguard Worker case ElfSymbol::SymbolType::FUNCTION:
89*9e3b08aeSAndroid Build Coastguard Worker return os << "function";
90*9e3b08aeSAndroid Build Coastguard Worker case ElfSymbol::SymbolType::COMMON:
91*9e3b08aeSAndroid Build Coastguard Worker return os << "common";
92*9e3b08aeSAndroid Build Coastguard Worker case ElfSymbol::SymbolType::TLS:
93*9e3b08aeSAndroid Build Coastguard Worker return os << "TLS";
94*9e3b08aeSAndroid Build Coastguard Worker case ElfSymbol::SymbolType::GNU_IFUNC:
95*9e3b08aeSAndroid Build Coastguard Worker return os << "indirect (ifunc) function";
96*9e3b08aeSAndroid Build Coastguard Worker }
97*9e3b08aeSAndroid Build Coastguard Worker }
98*9e3b08aeSAndroid Build Coastguard Worker
operator <<(std::ostream & os,ElfSymbol::Binding binding)99*9e3b08aeSAndroid Build Coastguard Worker std::ostream& operator<<(std::ostream& os, ElfSymbol::Binding binding) {
100*9e3b08aeSAndroid Build Coastguard Worker switch (binding) {
101*9e3b08aeSAndroid Build Coastguard Worker case ElfSymbol::Binding::GLOBAL:
102*9e3b08aeSAndroid Build Coastguard Worker return os << "global";
103*9e3b08aeSAndroid Build Coastguard Worker case ElfSymbol::Binding::LOCAL:
104*9e3b08aeSAndroid Build Coastguard Worker return os << "local";
105*9e3b08aeSAndroid Build Coastguard Worker case ElfSymbol::Binding::WEAK:
106*9e3b08aeSAndroid Build Coastguard Worker return os << "weak";
107*9e3b08aeSAndroid Build Coastguard Worker case ElfSymbol::Binding::GNU_UNIQUE:
108*9e3b08aeSAndroid Build Coastguard Worker return os << "GNU unique";
109*9e3b08aeSAndroid Build Coastguard Worker }
110*9e3b08aeSAndroid Build Coastguard Worker }
111*9e3b08aeSAndroid Build Coastguard Worker
operator <<(std::ostream & os,ElfSymbol::Visibility visibility)112*9e3b08aeSAndroid Build Coastguard Worker std::ostream& operator<<(std::ostream& os, ElfSymbol::Visibility visibility) {
113*9e3b08aeSAndroid Build Coastguard Worker switch (visibility) {
114*9e3b08aeSAndroid Build Coastguard Worker case ElfSymbol::Visibility::DEFAULT:
115*9e3b08aeSAndroid Build Coastguard Worker return os << "default";
116*9e3b08aeSAndroid Build Coastguard Worker case ElfSymbol::Visibility::PROTECTED:
117*9e3b08aeSAndroid Build Coastguard Worker return os << "protected";
118*9e3b08aeSAndroid Build Coastguard Worker case ElfSymbol::Visibility::HIDDEN:
119*9e3b08aeSAndroid Build Coastguard Worker return os << "hidden";
120*9e3b08aeSAndroid Build Coastguard Worker case ElfSymbol::Visibility::INTERNAL:
121*9e3b08aeSAndroid Build Coastguard Worker return os << "internal";
122*9e3b08aeSAndroid Build Coastguard Worker }
123*9e3b08aeSAndroid Build Coastguard Worker }
124*9e3b08aeSAndroid Build Coastguard Worker
VersionInfoToString(const ElfSymbol::VersionInfo & version_info)125*9e3b08aeSAndroid Build Coastguard Worker std::string VersionInfoToString(const ElfSymbol::VersionInfo& version_info) {
126*9e3b08aeSAndroid Build Coastguard Worker return '@' + std::string(version_info.is_default ? "@" : "") +
127*9e3b08aeSAndroid Build Coastguard Worker version_info.name;
128*9e3b08aeSAndroid Build Coastguard Worker }
129*9e3b08aeSAndroid Build Coastguard Worker
VersionedSymbolName(const ElfSymbol & symbol)130*9e3b08aeSAndroid Build Coastguard Worker std::string VersionedSymbolName(const ElfSymbol& symbol) {
131*9e3b08aeSAndroid Build Coastguard Worker return symbol.symbol_name + (symbol.version_info
132*9e3b08aeSAndroid Build Coastguard Worker ? VersionInfoToString(*symbol.version_info)
133*9e3b08aeSAndroid Build Coastguard Worker : std::string());
134*9e3b08aeSAndroid Build Coastguard Worker }
135*9e3b08aeSAndroid Build Coastguard Worker
operator <<(std::ostream & os,ElfSymbol::CRC crc)136*9e3b08aeSAndroid Build Coastguard Worker std::ostream& operator<<(std::ostream& os, ElfSymbol::CRC crc) {
137*9e3b08aeSAndroid Build Coastguard Worker return os << Hex(crc.number);
138*9e3b08aeSAndroid Build Coastguard Worker }
139*9e3b08aeSAndroid Build Coastguard Worker
operator <<(std::ostream & os,Primitive::Encoding encoding)140*9e3b08aeSAndroid Build Coastguard Worker std::ostream& operator<<(std::ostream& os, Primitive::Encoding encoding) {
141*9e3b08aeSAndroid Build Coastguard Worker switch (encoding) {
142*9e3b08aeSAndroid Build Coastguard Worker case Primitive::Encoding::BOOLEAN:
143*9e3b08aeSAndroid Build Coastguard Worker return os << "boolean";
144*9e3b08aeSAndroid Build Coastguard Worker case Primitive::Encoding::SIGNED_INTEGER:
145*9e3b08aeSAndroid Build Coastguard Worker return os << "signed integer";
146*9e3b08aeSAndroid Build Coastguard Worker case Primitive::Encoding::UNSIGNED_INTEGER:
147*9e3b08aeSAndroid Build Coastguard Worker return os << "unsigned integer";
148*9e3b08aeSAndroid Build Coastguard Worker case Primitive::Encoding::SIGNED_CHARACTER:
149*9e3b08aeSAndroid Build Coastguard Worker return os << "signed character";
150*9e3b08aeSAndroid Build Coastguard Worker case Primitive::Encoding::UNSIGNED_CHARACTER:
151*9e3b08aeSAndroid Build Coastguard Worker return os << "unsigned character";
152*9e3b08aeSAndroid Build Coastguard Worker case Primitive::Encoding::REAL_NUMBER:
153*9e3b08aeSAndroid Build Coastguard Worker return os << "real number";
154*9e3b08aeSAndroid Build Coastguard Worker case Primitive::Encoding::COMPLEX_NUMBER:
155*9e3b08aeSAndroid Build Coastguard Worker return os << "complex number";
156*9e3b08aeSAndroid Build Coastguard Worker case Primitive::Encoding::UTF:
157*9e3b08aeSAndroid Build Coastguard Worker return os << "UTF";
158*9e3b08aeSAndroid Build Coastguard Worker }
159*9e3b08aeSAndroid Build Coastguard Worker }
160*9e3b08aeSAndroid Build Coastguard Worker
161*9e3b08aeSAndroid Build Coastguard Worker } // namespace stg
162