Fix null dereference in OSAtomicChecker and special case SymbolicRegions.  We still aren't handling them correctly; I've added to failing test cases to test/Analysis/NSString-failed-cases.m that should pass and then be merged in to test/Analysis/NSString.m.


git-svn-id: https://llvm.org/svn/llvm-project/cfe/trunk@90993 91177308-0d34-0410-b5e6-96231b3b80d8
diff --git a/lib/Analysis/OSAtomicChecker.cpp b/lib/Analysis/OSAtomicChecker.cpp
index 03e9e38..5a89345 100644
--- a/lib/Analysis/OSAtomicChecker.cpp
+++ b/lib/Analysis/OSAtomicChecker.cpp
@@ -98,11 +98,20 @@
   ExplodedNodeSet Tmp;
   SVal location = state->getSVal(theValueExpr);
   // Here we should use the value type of the region as the load type.
-  const MemRegion *R = location.getAsRegion()->StripCasts();
   QualType LoadTy;
-  if (R) {
-    LoadTy = cast<TypedRegion>(R)->getValueType(Ctx);
-    location = loc::MemRegionVal(R);
+  if (const MemRegion *R = location.getAsRegion()) {
+    // We must be careful, as SymbolicRegions aren't typed.
+    const MemRegion *strippedR = R->StripCasts();
+    // FIXME: This isn't quite the right solution.  One test case in 'test/Analysis/NSString.m'
+    // is giving the wrong result.
+    const TypedRegion *typedR =
+      isa<SymbolicRegion>(strippedR) ? cast<TypedRegion>(R) :
+                                      dyn_cast<TypedRegion>(strippedR);
+    
+    if (typedR) {
+      LoadTy = typedR->getValueType(Ctx);
+      location = loc::MemRegionVal(typedR);
+    }
   }
   Engine.EvalLoad(Tmp, const_cast<Expr *>(theValueExpr), C.getPredecessor(), 
                   state, location, OSAtomicLoadTag, LoadTy);