[llvm] r261819 - [Support] Add a fancy helper function to get a static name for a type.

Chandler Carruth via llvm-commits llvm-commits at lists.llvm.org
Wed Feb 24 22:17:52 PST 2016


Thanks again David for the idea, done in r261827. And thanks for the
confirmation Kevin!

On Wed, Feb 24, 2016 at 10:10 PM Smith, Kevin B <kevin.b.smith at intel.com>
wrote:

> Yes, it does.  The intent of the Intel Compiler is to be completely
> compatible with the MSVC on windows, and with gcc on linux.  We have seen a
> number of instances, not in llvm, but in other open source software,
>
> where the #ifdefs used for __INTEL_COMPILER have been incorrect, and the
> code would have worked if the plain windows or gcc macros would have been
> used.
>
>
>
> I think David's solution is exactly right.
>
>
>
> Kevin Smith
>
>
>
> *From:* llvm-commits [mailto:llvm-commits-bounces at lists.llvm.org] *On
> Behalf Of *Chandler Carruth via llvm-commits
> *Sent:* Wednesday, February 24, 2016 8:34 PM
> *To:* David Majnemer <david.majnemer at gmail.com>; Chandler Carruth <
> chandlerc at gmail.com>
> *Cc:* llvm-commits <llvm-commits at lists.llvm.org>
> *Subject:* Re: [llvm] r261819 - [Support] Add a fancy helper function to
> get a static name for a type.
>
>
>
> Ah, if ICC defines __GNUC__ then we're golden. I'll make that change,
> thanks!
>
>
>
> On Wed, Feb 24, 2016 at 8:32 PM David Majnemer via llvm-commits <
> llvm-commits at lists.llvm.org> wrote:
>
> I think the handling for __INTEL_COMPILER is not quite right.
>
>
>
> Intel's compiler for Windows, icl, also defines __INTEL_COMPILER.
>
> While icl defines __PRETTY_FUNCTION__, it provides behavior compatible
> with __FUNCSIG__.
>
> Given that icc defines __GNUC__ and icl defines _MSC_VER, I'd suggest
> removing the defined(__INTEL_COMPILER).  I think the other checks will do
> the right thing.
>
>
>
>
>
> On Wed, Feb 24, 2016 at 7:58 PM, Chandler Carruth via llvm-commits <
> llvm-commits at lists.llvm.org> wrote:
>
> Author: chandlerc
> Date: Wed Feb 24 21:58:21 2016
> New Revision: 261819
>
> URL: http://llvm.org/viewvc/llvm-project?rev=261819&view=rev
> Log:
> [Support] Add a fancy helper function to get a static name for a type.
>
> This extracts the type name from __PRETTY_FUNCTION__ for compilers that
> support it (I've opted Clang, GCC, and ICC into this as I've tested that
> they work) and from __FUNCSIG__ which is very similar on MSVC. The
> routine falls back gracefully on a stub "UNKNOWN_TYPE" string with
> compilers or formats it doesn't understand.
>
> This should be enough for a lot of common cases in LLVM where the real
> goal is just to log or print a type name as a debugging aid, and save
> a ton of boilerplate in the process. Notably, I'm planning to use this
> to remove all the getName() boiler plate from the new pass manager.
>
> The design and implementation is based on a bunch of advice and
> discussion with Richard Smith and experimenting with most versions of
> Clang and GCC. David Majnemer also provided excellent advice on how best
> to do this with MSVC. Richard also checked that ICC does something
> reasonable and I'll watch the build bots for other compilers. It'd be
> great if someone could contribute logic for xlC and/or other toolchains.
>
> Differential Revision: http://reviews.llvm.org/D17565
>
> Added:
>     llvm/trunk/include/llvm/Support/TypeName.h
>     llvm/trunk/unittests/Support/TypeNameTest.cpp
> Modified:
>     llvm/trunk/unittests/Support/CMakeLists.txt
>
> Added: llvm/trunk/include/llvm/Support/TypeName.h
> URL:
> http://llvm.org/viewvc/llvm-project/llvm/trunk/include/llvm/Support/TypeName.h?rev=261819&view=auto
>
> ==============================================================================
> --- llvm/trunk/include/llvm/Support/TypeName.h (added)
> +++ llvm/trunk/include/llvm/Support/TypeName.h Wed Feb 24 21:58:21 2016
> @@ -0,0 +1,65 @@
> +//===- TypeName.h -----------------------------------------------*- C++
> -*-===//
> +//
> +//                     The LLVM Compiler Infrastructure
> +//
> +// This file is distributed under the University of Illinois Open Source
> +// License. See LICENSE.TXT for details.
> +//
>
> +//===----------------------------------------------------------------------===//
> +
> +#ifndef LLVM_SUPPORT_TYPENAME_H
> +#define LLVM_SUPPORT_TYPENAME_H
> +
> +#include "llvm/ADT/StringRef.h"
> +
> +namespace llvm {
> +
> +/// We provide a function which tries to compute the (demangled) name of
> a type
> +/// statically.
> +///
> +/// This routine may fail on some platforms or for particularly unusual
> types.
> +/// Do not use it for anything other than logging and debugging aids. It
> isn't
> +/// portable or dependendable in any real sense.
> +///
> +/// The returned StringRef will point into a static storage duration
> string.
> +/// However, it may not be null terminated and may be some strangely
> aligned
> +/// inner substring of a larger string.
> +template <typename DesiredTypeName>
> +inline StringRef getTypeName() {
> +#if defined(__clang__) || defined(__GNUC__) || defined(__INTEL_COMPILER)
> +  StringRef Name = __PRETTY_FUNCTION__;
> +
> +  StringRef Key = "DesiredTypeName = ";
> +  Name = Name.substr(Name.find(Key));
> +  assert(!Name.empty() && "Unable to find the template parameter!");
> +  Name = Name.drop_front(Key.size());
> +
> +  assert(Name.endswith("]") && "Name doesn't end in the substitution
> key!");
> +  return Name.drop_back(1);
> +#elif defined(_MSC_VER)
> +  StringRef Name = __FUNCSIG__;
> +
> +  StringRef Key = "getTypeName<";
> +  Name = Name.substr(Name.find(Key));
> +  assert(!Name.empty() && "Unable to find the function name!");
> +  Name = Name.drop_front(Key.size());
> +
> +  for (StringRef Prefix : {"class ", "struct ", "union ", "enum "})
> +    if (Name.startswith(Prefix)) {
> +      Name = Name.drop_front(Prefix.size());
> +      break;
> +    }
> +
> +  auto AnglePos = Name.rfind('>');
> +  assert(AnglePos != StringRef::npos && "Unable to find the closing
> '>'!");
> +  return Name.substr(0, AnglePos);
> +#else
> +  // No known technique for statically extracting a type name on this
> compiler.
> +  // We return a string that is unlikely to look like any type in LLVM.
> +  return "UNKNOWN_TYPE";
> +#endif
> +}
> +
> +}
> +
> +#endif
>
> Modified: llvm/trunk/unittests/Support/CMakeLists.txt
> URL:
> http://llvm.org/viewvc/llvm-project/llvm/trunk/unittests/Support/CMakeLists.txt?rev=261819&r1=261818&r2=261819&view=diff
>
> ==============================================================================
> --- llvm/trunk/unittests/Support/CMakeLists.txt (original)
> +++ llvm/trunk/unittests/Support/CMakeLists.txt Wed Feb 24 21:58:21 2016
> @@ -42,6 +42,7 @@ add_llvm_unittest(SupportTests
>    ThreadPool.cpp
>    TimerTest.cpp
>    TimeValueTest.cpp
> +  TypeNameTest.cpp
>    TrailingObjectsTest.cpp
>    UnicodeTest.cpp
>    YAMLIOTest.cpp
>
> Added: llvm/trunk/unittests/Support/TypeNameTest.cpp
> URL:
> http://llvm.org/viewvc/llvm-project/llvm/trunk/unittests/Support/TypeNameTest.cpp?rev=261819&view=auto
>
> ==============================================================================
> --- llvm/trunk/unittests/Support/TypeNameTest.cpp (added)
> +++ llvm/trunk/unittests/Support/TypeNameTest.cpp Wed Feb 24 21:58:21 2016
> @@ -0,0 +1,49 @@
> +//===- TypeNameTest.cpp
> ---------------------------------------------------===//
> +//
> +//                     The LLVM Compiler Infrastructure
> +//
> +// This file is distributed under the University of Illinois Open Source
> +// License. See LICENSE.TXT for details.
> +//
>
> +//===----------------------------------------------------------------------===//
> +
> +#include "llvm/Support/TypeName.h"
> +#include "llvm/Support/raw_ostream.h"
> +#include "gtest/gtest.h"
> +
> +using namespace llvm;
> +
> +namespace {
> +namespace N1 {
> +struct S1 {};
> +class C1 {};
> +union U1 {};
> +}
> +
> +TEST(TypeNameTest, Names) {
> +  struct S2 {};
> +
> +  StringRef S1Name = getTypeName<N1::S1>();
> +  StringRef C1Name = getTypeName<N1::C1>();
> +  StringRef U1Name = getTypeName<N1::U1>();
> +  StringRef S2Name = getTypeName<S2>();
> +
> +#if defined(__clang__) || defined(__GNUC__) || defined(__INTEL_COMPILER)
> ||    \
> +    defined(_MSC_VER)
> +  EXPECT_TRUE(S1Name.endswith("::N1::S1")) << S1Name.str();
> +  EXPECT_TRUE(C1Name.endswith("::N1::C1")) << C1Name.str();
> +  EXPECT_TRUE(U1Name.endswith("::N1::U1")) << U1Name.str();
> +#ifdef __clang__
> +  EXPECT_TRUE(S2Name.endswith("S2")) << S2Name.str();
> +#else
> +  EXPECT_TRUE(S2Name.endswith("::S2")) << S2Name.str();
> +#endif
> +#else
> +  EXPECT_EQ("UNKNOWN_TYPE", S1Name);
> +  EXPECT_EQ("UNKNOWN_TYPE", C1Name);
> +  EXPECT_EQ("UNKNOWN_TYPE", U1Name);
> +  EXPECT_EQ("UNKNOWN_TYPE", S2Name);
> +#endif
> +}
> +
> +} // end anonymous namespace
>
>
> _______________________________________________
> llvm-commits mailing list
> llvm-commits at lists.llvm.org
> http://lists.llvm.org/cgi-bin/mailman/listinfo/llvm-commits
>
>
>
> _______________________________________________
> llvm-commits mailing list
> llvm-commits at lists.llvm.org
> http://lists.llvm.org/cgi-bin/mailman/listinfo/llvm-commits
>
>
-------------- next part --------------
An HTML attachment was scrubbed...
URL: <http://lists.llvm.org/pipermail/llvm-commits/attachments/20160225/6fa1bf1e/attachment-0001.html>


More information about the llvm-commits mailing list