From cded725cbea9047bf9793b73432dc8528be36683 Mon Sep 17 00:00:00 2001 From: David Blaikie Date: Mon, 11 Mar 2019 23:10:33 +0000 Subject: [PATCH] Hexagon RDF: Replace function template (plus explicit specializations) with non-template overloads MIME-Version: 1.0 Content-Type: text/plain; charset=utf8 Content-Transfer-Encoding: 8bit For the design in question, overloads seem to be a much simpler and less subtle solution. This removes ODR issues, and errors of the kind where code that uses the specialization in question will accidentally and erroneously specialize the primary template. This only "works" by accident; the program is ill-formed NDR. (Found with -Wundefined-func-template.) Patch by Thomas Köppe! Differential Revision: https://reviews.llvm.org/D58998 git-svn-id: https://llvm.org/svn/llvm-project/llvm/trunk@355880 91177308-0d34-0410-b5e6-96231b3b80d8 --- lib/Target/Hexagon/RDFGraph.cpp | 22 ++-------------------- lib/Target/Hexagon/RDFGraph.h | 27 +++++++++++++++++++++++---- lib/Target/Hexagon/RDFLiveness.cpp | 1 - lib/Target/Hexagon/RDFLiveness.h | 2 ++ 4 files changed, 27 insertions(+), 25 deletions(-) diff --git a/lib/Target/Hexagon/RDFGraph.cpp b/lib/Target/Hexagon/RDFGraph.cpp index 18ceef5b718..9d8f706b8a0 100644 --- a/lib/Target/Hexagon/RDFGraph.cpp +++ b/lib/Target/Hexagon/RDFGraph.cpp @@ -54,7 +54,6 @@ raw_ostream &operator<< (raw_ostream &OS, const PrintLaneMaskOpt &P) { return OS; } -template<> raw_ostream &operator<< (raw_ostream &OS, const Print &P) { auto &TRI = P.G.getTRI(); if (P.Obj.Reg > 0 && P.Obj.Reg < TRI.getNumRegs()) @@ -65,7 +64,6 @@ raw_ostream &operator<< (raw_ostream &OS, const Print &P) { return OS; } -template<> raw_ostream &operator<< (raw_ostream &OS, const Print &P) { auto NA = P.G.addr(P.Obj); uint16_t Attrs = NA.Addr->getAttrs(); @@ -115,7 +113,6 @@ static void printRefHeader(raw_ostream &OS, const NodeAddr RA, OS << '!'; } -template<> raw_ostream &operator<< (raw_ostream &OS, const Print> &P) { printRefHeader(OS, P.Obj, P.G); OS << '('; @@ -133,7 +130,6 @@ raw_ostream &operator<< (raw_ostream &OS, const Print> &P) { return OS; } -template<> raw_ostream &operator<< (raw_ostream &OS, const Print> &P) { printRefHeader(OS, P.Obj, P.G); OS << '('; @@ -145,7 +141,6 @@ raw_ostream &operator<< (raw_ostream &OS, const Print> &P) { return OS; } -template<> raw_ostream &operator<< (raw_ostream &OS, const Print> &P) { printRefHeader(OS, P.Obj, P.G); @@ -161,7 +156,6 @@ raw_ostream &operator<< (raw_ostream &OS, return OS; } -template<> raw_ostream &operator<< (raw_ostream &OS, const Print> &P) { switch (P.Obj.Addr->getKind()) { case NodeAttrs::Def: @@ -177,7 +171,6 @@ raw_ostream &operator<< (raw_ostream &OS, const Print> &P) { return OS; } -template<> raw_ostream &operator<< (raw_ostream &OS, const Print &P) { unsigned N = P.Obj.size(); for (auto I : P.Obj) { @@ -188,7 +181,6 @@ raw_ostream &operator<< (raw_ostream &OS, const Print &P) { return OS; } -template<> raw_ostream &operator<< (raw_ostream &OS, const Print &P) { unsigned N = P.Obj.size(); for (auto I : P.Obj) { @@ -223,16 +215,13 @@ namespace { } // end anonymous namespace -template<> raw_ostream &operator<< (raw_ostream &OS, const Print> &P) { OS << Print(P.Obj.Id, P.G) << ": phi [" << PrintListV(P.Obj.Addr->members(P.G), P.G) << ']'; return OS; } -template<> -raw_ostream &operator<< (raw_ostream &OS, - const Print> &P) { +raw_ostream &operator<<(raw_ostream &OS, const Print> &P) { const MachineInstr &MI = *P.Obj.Addr->getCode(); unsigned Opc = MI.getOpcode(); OS << Print(P.Obj.Id, P.G) << ": " << P.G.getTII().getName(Opc); @@ -257,7 +246,6 @@ raw_ostream &operator<< (raw_ostream &OS, return OS; } -template<> raw_ostream &operator<< (raw_ostream &OS, const Print> &P) { switch (P.Obj.Addr->getKind()) { @@ -274,7 +262,6 @@ raw_ostream &operator<< (raw_ostream &OS, return OS; } -template<> raw_ostream &operator<< (raw_ostream &OS, const Print> &P) { MachineBasicBlock *BB = P.Obj.Addr->getCode(); @@ -308,9 +295,7 @@ raw_ostream &operator<< (raw_ostream &OS, return OS; } -template<> -raw_ostream &operator<< (raw_ostream &OS, - const Print> &P) { +raw_ostream &operator<<(raw_ostream &OS, const Print> &P) { OS << "DFG dump:[\n" << Print(P.Obj.Id, P.G) << ": Function: " << P.Obj.Addr->getCode()->getName() << '\n'; for (auto I : P.Obj.Addr->members(P.G)) @@ -319,7 +304,6 @@ raw_ostream &operator<< (raw_ostream &OS, return OS; } -template<> raw_ostream &operator<< (raw_ostream &OS, const Print &P) { OS << '{'; for (auto I : P.Obj) @@ -328,13 +312,11 @@ raw_ostream &operator<< (raw_ostream &OS, const Print &P) { return OS; } -template<> raw_ostream &operator<< (raw_ostream &OS, const Print &P) { P.Obj.print(OS); return OS; } -template<> raw_ostream &operator<< (raw_ostream &OS, const Print &P) { for (auto I = P.Obj.top(), E = P.Obj.bottom(); I != E; ) { diff --git a/lib/Target/Hexagon/RDFGraph.h b/lib/Target/Hexagon/RDFGraph.h index e91dff084b8..585f43e116f 100644 --- a/lib/Target/Hexagon/RDFGraph.h +++ b/lib/Target/Hexagon/RDFGraph.h @@ -924,10 +924,6 @@ namespace rdf { return MM; } - template struct Print; - template - raw_ostream &operator<< (raw_ostream &OS, const Print &P); - template struct Print { Print(const T &x, const DataFlowGraph &g) : Obj(x), G(g) {} @@ -942,6 +938,29 @@ namespace rdf { : Print>(x, g) {} }; + raw_ostream &operator<<(raw_ostream &OS, const Print &P); + raw_ostream &operator<<(raw_ostream &OS, const Print &P); + raw_ostream &operator<<(raw_ostream &OS, const Print> &P); + raw_ostream &operator<<(raw_ostream &OS, const Print> &P); + raw_ostream &operator<<(raw_ostream &OS, + const Print> &P); + raw_ostream &operator<<(raw_ostream &OS, const Print> &P); + raw_ostream &operator<<(raw_ostream &OS, const Print &P); + raw_ostream &operator<<(raw_ostream &OS, const Print &P); + raw_ostream &operator<<(raw_ostream &OS, const Print> &P); + raw_ostream &operator<<(raw_ostream &OS, + const Print> &P); + raw_ostream &operator<<(raw_ostream &OS, + const Print> &P); + raw_ostream &operator<<(raw_ostream &OS, + const Print> &P); + raw_ostream &operator<<(raw_ostream &OS, + const Print> &P); + raw_ostream &operator<<(raw_ostream &OS, const Print &P); + raw_ostream &operator<<(raw_ostream &OS, const Print &P); + raw_ostream &operator<<(raw_ostream &OS, + const Print &P); + } // end namespace rdf } // end namespace llvm diff --git a/lib/Target/Hexagon/RDFLiveness.cpp b/lib/Target/Hexagon/RDFLiveness.cpp index 6a3c82566ba..9cd304aa10b 100644 --- a/lib/Target/Hexagon/RDFLiveness.cpp +++ b/lib/Target/Hexagon/RDFLiveness.cpp @@ -57,7 +57,6 @@ static cl::opt MaxRecNest("rdf-liveness-max-rec", cl::init(25), namespace llvm { namespace rdf { - template<> raw_ostream &operator<< (raw_ostream &OS, const Print &P) { OS << '{'; for (auto &I : P.Obj) { diff --git a/lib/Target/Hexagon/RDFLiveness.h b/lib/Target/Hexagon/RDFLiveness.h index a66e7ad7513..ea489027172 100644 --- a/lib/Target/Hexagon/RDFLiveness.h +++ b/lib/Target/Hexagon/RDFLiveness.h @@ -142,6 +142,8 @@ namespace rdf { unsigned Nest, unsigned MaxNest); }; + raw_ostream &operator<<(raw_ostream &OS, const Print &P); + } // end namespace rdf } // end namespace llvm -- 2.50.1