[llvm] r227284 - Move EH personality type classification to Analysis/LibCallSemantics.h

Reid Kleckner reid at kleckner.net
Tue Jan 27 17:17:38 PST 2015


Author: rnk
Date: Tue Jan 27 19:17:38 2015
New Revision: 227284

URL: http://llvm.org/viewvc/llvm-project?rev=227284&view=rev
Log:
Move EH personality type classification to Analysis/LibCallSemantics.h

Summary:
Also add enum types for __C_specific_handler and _CxxFrameHandler3 for
which we know a few things.

Reviewers: majnemer

Subscribers: llvm-commits

Differential Revision: http://reviews.llvm.org/D7214

Modified:
    llvm/trunk/include/llvm/Analysis/LibCallSemantics.h
    llvm/trunk/lib/Analysis/LibCallSemantics.cpp
    llvm/trunk/lib/Transforms/InstCombine/InstructionCombining.cpp
    llvm/trunk/test/Transforms/InstCombine/LandingPadClauses.ll

Modified: llvm/trunk/include/llvm/Analysis/LibCallSemantics.h
URL: http://llvm.org/viewvc/llvm-project/llvm/trunk/include/llvm/Analysis/LibCallSemantics.h?rev=227284&r1=227283&r2=227284&view=diff
==============================================================================
--- llvm/trunk/include/llvm/Analysis/LibCallSemantics.h (original)
+++ llvm/trunk/include/llvm/Analysis/LibCallSemantics.h Tue Jan 27 19:17:38 2015
@@ -162,6 +162,21 @@ namespace llvm {
     virtual const LibCallFunctionInfo *getFunctionInfoArray() const = 0;
   };
 
+  enum class EHPersonality {
+    Unknown,
+    GNU_Ada,
+    GNU_C,
+    GNU_CXX,
+    GNU_ObjC,
+    MSVC_Win64SEH,
+    MSVC_CXX,
+  };
+
+  /// ClassifyEHPersonality - See if the given exception handling personality
+  /// function is one that we understand.  If so, return a description of it;
+  /// otherwise return Unknown_Personality.
+  EHPersonality ClassifyEHPersonality(Value *Pers);
+
 } // end namespace llvm
 
 #endif

Modified: llvm/trunk/lib/Analysis/LibCallSemantics.cpp
URL: http://llvm.org/viewvc/llvm-project/llvm/trunk/lib/Analysis/LibCallSemantics.cpp?rev=227284&r1=227283&r2=227284&view=diff
==============================================================================
--- llvm/trunk/lib/Analysis/LibCallSemantics.cpp (original)
+++ llvm/trunk/lib/Analysis/LibCallSemantics.cpp Tue Jan 27 19:17:38 2015
@@ -15,6 +15,7 @@
 
 #include "llvm/Analysis/LibCallSemantics.h"
 #include "llvm/ADT/StringMap.h"
+#include "llvm/ADT/StringSwitch.h"
 #include "llvm/IR/Function.h"
 using namespace llvm;
 
@@ -61,3 +62,18 @@ LibCallInfo::getFunctionInfo(const Funct
   return Map->lookup(F->getName());
 }
 
+/// See if the given exception handling personality function is one that we
+/// understand.  If so, return a description of it; otherwise return Unknown.
+EHPersonality llvm::ClassifyEHPersonality(Value *Pers) {
+  Function *F = dyn_cast<Function>(Pers->stripPointerCasts());
+  if (!F)
+    return EHPersonality::Unknown;
+  return StringSwitch<EHPersonality>(F->getName())
+    .Case("__gnat_eh_personality", EHPersonality::GNU_Ada)
+    .Case("__gxx_personality_v0",  EHPersonality::GNU_CXX)
+    .Case("__gcc_personality_v0",  EHPersonality::GNU_C)
+    .Case("__objc_personality_v0", EHPersonality::GNU_ObjC)
+    .Case("__C_specific_handler",  EHPersonality::MSVC_Win64SEH)
+    .Case("__CxxFrameHandler3",    EHPersonality::MSVC_CXX)
+    .Default(EHPersonality::Unknown);
+}

Modified: llvm/trunk/lib/Transforms/InstCombine/InstructionCombining.cpp
URL: http://llvm.org/viewvc/llvm-project/llvm/trunk/lib/Transforms/InstCombine/InstructionCombining.cpp?rev=227284&r1=227283&r2=227284&view=diff
==============================================================================
--- llvm/trunk/lib/Transforms/InstCombine/InstructionCombining.cpp (original)
+++ llvm/trunk/lib/Transforms/InstCombine/InstructionCombining.cpp Tue Jan 27 19:17:38 2015
@@ -43,6 +43,7 @@
 #include "llvm/Analysis/CFG.h"
 #include "llvm/Analysis/ConstantFolding.h"
 #include "llvm/Analysis/InstructionSimplify.h"
+#include "llvm/Analysis/LibCallSemantics.h"
 #include "llvm/Analysis/LoopInfo.h"
 #include "llvm/Analysis/MemoryBuiltins.h"
 #include "llvm/Analysis/TargetLibraryInfo.h"
@@ -2259,41 +2260,26 @@ Instruction *InstCombiner::visitExtractV
   return nullptr;
 }
 
-enum Personality_Type {
-  Unknown_Personality,
-  GNU_Ada_Personality,
-  GNU_CXX_Personality,
-  GNU_ObjC_Personality
-};
-
-/// RecognizePersonality - See if the given exception handling personality
-/// function is one that we understand.  If so, return a description of it;
-/// otherwise return Unknown_Personality.
-static Personality_Type RecognizePersonality(Value *Pers) {
-  Function *F = dyn_cast<Function>(Pers->stripPointerCasts());
-  if (!F)
-    return Unknown_Personality;
-  return StringSwitch<Personality_Type>(F->getName())
-    .Case("__gnat_eh_personality", GNU_Ada_Personality)
-    .Case("__gxx_personality_v0",  GNU_CXX_Personality)
-    .Case("__objc_personality_v0", GNU_ObjC_Personality)
-    .Default(Unknown_Personality);
-}
-
 /// isCatchAll - Return 'true' if the given typeinfo will match anything.
-static bool isCatchAll(Personality_Type Personality, Constant *TypeInfo) {
+static bool isCatchAll(EHPersonality Personality, Constant *TypeInfo) {
   switch (Personality) {
-  case Unknown_Personality:
+  case EHPersonality::GNU_C:
+    // The GCC C EH personality only exists to support cleanups, so it's not
+    // clear what the semantics of catch clauses are.
+    return false;
+  case EHPersonality::Unknown:
     return false;
-  case GNU_Ada_Personality:
+  case EHPersonality::GNU_Ada:
     // While __gnat_all_others_value will match any Ada exception, it doesn't
     // match foreign exceptions (or didn't, before gcc-4.7).
     return false;
-  case GNU_CXX_Personality:
-  case GNU_ObjC_Personality:
+  case EHPersonality::GNU_CXX:
+  case EHPersonality::GNU_ObjC:
+  case EHPersonality::MSVC_Win64SEH:
+  case EHPersonality::MSVC_CXX:
     return TypeInfo->isNullValue();
   }
-  llvm_unreachable("Unknown personality!");
+  llvm_unreachable("invalid enum");
 }
 
 static bool shorter_filter(const Value *LHS, const Value *RHS) {
@@ -2307,7 +2293,7 @@ Instruction *InstCombiner::visitLandingP
   // The logic here should be correct for any real-world personality function.
   // However if that turns out not to be true, the offending logic can always
   // be conditioned on the personality function, like the catch-all logic is.
-  Personality_Type Personality = RecognizePersonality(LI.getPersonalityFn());
+  EHPersonality Personality = ClassifyEHPersonality(LI.getPersonalityFn());
 
   // Simplify the list of clauses, eg by removing repeated catch clauses
   // (these are often created by inlining).

Modified: llvm/trunk/test/Transforms/InstCombine/LandingPadClauses.ll
URL: http://llvm.org/viewvc/llvm-project/llvm/trunk/test/Transforms/InstCombine/LandingPadClauses.ll?rev=227284&r1=227283&r2=227284&view=diff
==============================================================================
--- llvm/trunk/test/Transforms/InstCombine/LandingPadClauses.ll (original)
+++ llvm/trunk/test/Transforms/InstCombine/LandingPadClauses.ll Tue Jan 27 19:17:38 2015
@@ -7,6 +7,7 @@
 declare i32 @generic_personality(i32, i64, i8*, i8*)
 declare i32 @__gxx_personality_v0(i32, i64, i8*, i8*)
 declare i32 @__objc_personality_v0(i32, i64, i8*, i8*)
+declare i32 @__C_specific_handler(...)
 
 declare void @bar()
 
@@ -227,6 +228,57 @@ lpad.d:
           cleanup
           catch i32* null
   unreachable
+; CHECK: %d = landingpad
+; CHECK-NEXT: null
+; CHECK-NEXT: unreachable
+}
+
+define void @foo_seh() {
+; CHECK-LABEL: @foo_seh(
+  invoke void @bar()
+    to label %cont.a unwind label %lpad.a
+cont.a:
+  invoke void @bar()
+    to label %cont.b unwind label %lpad.b
+cont.b:
+  invoke void @bar()
+    to label %cont.c unwind label %lpad.c
+cont.c:
+  invoke void @bar()
+    to label %cont.d unwind label %lpad.d
+cont.d:
+  ret void
+
+lpad.a:
+  %a = landingpad { i8*, i32 } personality i32 (...)* @__C_specific_handler
+          catch i32* null
+          catch i32* @T1
+  unreachable
+; CHECK: %a = landingpad
+; CHECK-NEXT: null
+; CHECK-NEXT: unreachable
+
+lpad.b:
+  %b = landingpad { i8*, i32 } personality i32 (...)* @__C_specific_handler
+          filter [1 x i32*] zeroinitializer
+  unreachable
+; CHECK: %b = landingpad
+; CHECK-NEXT: cleanup
+; CHECK-NEXT: unreachable
+
+lpad.c:
+  %c = landingpad { i8*, i32 } personality i32 (...)* @__C_specific_handler
+          filter [2 x i32*] [i32* @T1, i32* null]
+  unreachable
+; CHECK: %c = landingpad
+; CHECK-NEXT: cleanup
+; CHECK-NEXT: unreachable
+
+lpad.d:
+  %d = landingpad { i8*, i32 } personality i32 (...)* @__C_specific_handler
+          cleanup
+          catch i32* null
+  unreachable
 ; CHECK: %d = landingpad
 ; CHECK-NEXT: null
 ; CHECK-NEXT: unreachable





More information about the llvm-commits mailing list