[PATCH] D33125: Introduce isoneof<T0, T1, ...> as an extension of isa<T>

serge via Phabricator via llvm-commits llvm-commits at lists.llvm.org
Mon May 22 05:33:27 PDT 2017


serge-sans-paille updated this revision to Diff 99745.
serge-sans-paille edited the summary of this revision.
serge-sans-paille added a comment.

@chandlerc Here is a minimal version of the patch, with the minimal hackery to support the ``isa<anyof<...>>`` syntax. Note that it should support ``isa<anyof<>>`` (which is always false) and ``isa<anyof<T>>`` which should be quivalent to ``isa<T>``.


Repository:
  rL LLVM

https://reviews.llvm.org/D33125

Files:
  include/llvm/IR/Value.h
  include/llvm/Support/Casting.h


Index: include/llvm/IR/Value.h
===================================================================
--- include/llvm/IR/Value.h
+++ include/llvm/IR/Value.h
@@ -802,19 +802,19 @@
 
 template <> struct isa_impl<GlobalIndirectSymbol, Value> {
   static inline bool doit(const Value &Val) {
-    return isa<GlobalAlias>(Val) || isa<GlobalIFunc>(Val);
+    return isa<anyof<GlobalAlias, GlobalIFunc>>(Val);
   }
 };
 
 template <> struct isa_impl<GlobalValue, Value> {
   static inline bool doit(const Value &Val) {
-    return isa<GlobalObject>(Val) || isa<GlobalIndirectSymbol>(Val);
+    return isa<anyof<GlobalObject, GlobalIndirectSymbol>>(Val);
   }
 };
 
 template <> struct isa_impl<GlobalObject, Value> {
   static inline bool doit(const Value &Val) {
-    return isa<GlobalVariable>(Val) || isa<Function>(Val);
+    return isa<anyof<GlobalVariable, Function>>(Val);
   }
 };
 
Index: include/llvm/Support/Casting.h
===================================================================
--- include/llvm/Support/Casting.h
+++ include/llvm/Support/Casting.h
@@ -132,14 +132,37 @@
   }
 };
 
+template <typename... Tys> struct anyof {};
+
+template <class X, class Y> inline bool isa_impl_dispatcher(const Y &Val, X *) {
+  return isa_impl_wrap<X, const Y,
+                       typename simplify_type<const Y>::SimpleType>::doit(Val);
+}
+
+template <class X, class... Xs, class Y>
+inline bool isa_impl_dispatcher(const Y &Val, anyof<X, Xs...> *) {
+  return isa_impl_dispatcher(Val, (X *)nullptr) ||
+         isa_impl_dispatcher(Val, (anyof<Xs...> *)nullptr);
+}
+template <class Y> inline bool isa_impl_dispatcher(const Y &Val, anyof<> *) {
+  return false;
+}
+
 // isa<X> - Return true if the parameter to the template is an instance of the
 // template type argument.  Used like this:
 //
 //  if (isa<Type>(myVal)) { ... }
 //
+// If type is of the form anyof<Type0, Type1, Type2> as in:
+//
+//  if (isa<anyof<Type0, Type1, Type2>>(myVal)) { ... }
+//
+// Then the construct is equivalent to:
+//
+//  if (isa<Type0>(myVal) || isa<Type1>(myVal) || isa<Type2>(myVal)) { ... }
+//
 template <class X, class Y> LLVM_NODISCARD inline bool isa(const Y &Val) {
-  return isa_impl_wrap<X, const Y,
-                       typename simplify_type<const Y>::SimpleType>::doit(Val);
+  return isa_impl_dispatcher(Val, (X *)nullptr);
 }
 
 //===----------------------------------------------------------------------===//


-------------- next part --------------
A non-text attachment was scrubbed...
Name: D33125.99745.patch
Type: text/x-patch
Size: 2419 bytes
Desc: not available
URL: <http://lists.llvm.org/pipermail/llvm-commits/attachments/20170522/48901395/attachment.bin>


More information about the llvm-commits mailing list