[cfe-dev] [Proposal]: Fast non-portable extension to retrieve a type name from a pointer as a GV: __builtin_type_name(T* Ptr, [int Style])

James Y Knight via cfe-dev cfe-dev at lists.llvm.org
Tue Sep 4 14:42:10 PDT 2018


As discussed on IRC, ISTM this would be better spelled as:
  typeid(<typename>).name();

The issue with that at the moment is that typeid() is an error if you build
with -fno-rtti. However, there appears to be no reason why we cannot
support `typeid(<typename>)` even with -fno-rtti. Unlike
`typeid(<variable>)`, it requires no extra data to be emitted, since
there's no possibility that dynamic dispatch is required. Therefore,
similarly to how exception support still functions with -fno-rtti by
emitting the explicitly required typeinfo data on demand, so too can
typeid(<typename>).

I note also that when .name() is the only value used, the remainder of the
typeinfo data is already omitted from the output when compiling with
optimizations.

It looks like supporting this would be only be a few line change in clang,
since all the underlying infrastructure is there already to support the EH
with -fno-rtti use-case.

On Mon, Sep 3, 2018 at 10:41 AM via cfe-dev <cfe-dev at lists.llvm.org> wrote:

> The concept itself is pretty trivial, the builtin takes one or two
> arguments, one of which
> has to be a pointer to an arbitrary type, this makes it particularly
> useful with C++
> auto declarations or even printing the type by simply casting a null
> pointer to
> the type in question. It's qualifiers are retained for the sake of
> printing them
> depending on the requested style.
>
> Implementation
> ^^^^^^^^^^^^^^
>
> const char* TypeName =  __builtin_type_name(T* Ptr, [int Style])
>
> After validating either 1 or 2 argument form (ie. Pointed to type, and
> whether it's a
> record declaration), SemaChecking will set the return type to
> TheCall->setType(
> Context.getPointerType(Context.CharTy.withConst())) leaving it for Clang's
> CodeGen
> to deal with.
>
> Second argument is used to control the output format in form of a bitmask
> passed down to PrintingPolicy (as I port this I will decouple the values
> so the
> builtin's behavior isn't dependent on further changes in PrintingPolicy.
> At
> which point the type is retrieved using `getAsString` and stored in the
> CGM
> with `GetAddrOfConstantCString` allowing coalescing of those strings later
> during linking. as it's cast to a Int8Ptr.
>
> This is all done in Clang without needing to add anything to the LLVM core.
>
> Things left to do before submitting for code review
> ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^
> * There is no test coverage, so I need to write up a test file,
> comprehensively
>   testing cases I haven't considered before like Objective-C pointers, any
>   pointer to a special Clang type that may behave unexpectedly, complex
>   C++ templates (or simple ones, was my main use of it). Target is IR since
>   Clang fully lowers it, so in theory it's platform agnostic providing
> there is
>   enough space (the original use was for Embedded C++ with no RTTI.
> * While this is out of scope, a GUID buffer as a a style would provide a
> form
>   type IDs in absence of RTTI or alternatively smaller types like u32 or
> u16
>   (aimed at single module builds where they can remain unique, ie. embedded
>   systems with a kernel using those to represent kernel object types).
>
> Rationale
> ^^^^^^^^^
> It's clear that this functionality is desired outside of embedded domain,
> typically with hacks involving a lambda and __PRETTY_FUNCTION__, on case
> being in `lib/Support/TypeName.h` in LLVMSupport. Many non-portable hacks
> that depend on compiler versions exist. This doesn't aim to be portable,
> just to be compact, not have a runtime cost, and provide this information
> either for debugging or even for more practical reasons.
>
> I wanted to find out if there was interest in this kind of thing since
> I have developed a variety of different useful and not so useful
> extensions,
> originally for embedded use but I want to upstream them for general use,
> I want to know what the consensus is on 1) This particular extension
> 2). Further extensions that were originally developed for embedded use
> but have turned out to be useful in a lot of contexts where you are willing
> to sacrifice portability  (now with `__has_builtin` this is extremely easy
> to
> test for and fallback on something else).
>
> On the other hand it's a lot to do overall so I would prefer to get a
> consensus
> whether each feature (even this small one) is worth cleaning up and putting
> up for code review, since I understand that something like builtin bloat
> or non portability may be of concern. As for the formal name I'd like to
> call
> it extensions for Embedded C++ 2 gating it behind an opt-in flag such as
> `-fecxx2-extensions`.
>
> Other things involve limited reflection retrieving the bare minimum that's
> needed, a llvm::formatv style formatter accelerator, getting names of
> record
> scope at different levels with 0 being similar to the desired
> __CLASSNAME__
> macro (at least by some).
>
> Looking forward to any feedback whether positive or negative.
> Thank you for your time.
> - Kristina
>
> _______________________________________________
> cfe-dev mailing list
> cfe-dev at lists.llvm.org
> http://lists.llvm.org/cgi-bin/mailman/listinfo/cfe-dev
>
-------------- next part --------------
An HTML attachment was scrubbed...
URL: <http://lists.llvm.org/pipermail/cfe-dev/attachments/20180904/44d0319b/attachment.html>


More information about the cfe-dev mailing list