r338809 - [libclang 4/8] Add the clang_Type_getNullability() API

Michael Wu via cfe-commits cfe-commits at lists.llvm.org
Thu Aug 2 21:38:04 PDT 2018


Author: mwu
Date: Thu Aug  2 21:38:04 2018
New Revision: 338809

URL: http://llvm.org/viewvc/llvm-project?rev=338809&view=rev
Log:
[libclang 4/8] Add the clang_Type_getNullability() API

Summary:
This patch adds a clang-c API for querying the nullability of an AttributedType.

The test here also tests D49081

Reviewers: yvvan, jbcoe

Reviewed By: yvvan

Subscribers: cfe-commits

Differential Revision: https://reviews.llvm.org/D49082

Added:
    cfe/trunk/test/Index/nullability.c
Modified:
    cfe/trunk/include/clang-c/Index.h
    cfe/trunk/tools/c-index-test/c-index-test.c
    cfe/trunk/tools/libclang/CXType.cpp
    cfe/trunk/tools/libclang/libclang.exports

Modified: cfe/trunk/include/clang-c/Index.h
URL: http://llvm.org/viewvc/llvm-project/cfe/trunk/include/clang-c/Index.h?rev=338809&r1=338808&r2=338809&view=diff
==============================================================================
--- cfe/trunk/include/clang-c/Index.h (original)
+++ cfe/trunk/include/clang-c/Index.h Thu Aug  2 21:38:04 2018
@@ -3745,6 +3745,33 @@ CINDEX_LINKAGE CXType clang_Type_getName
  */
 CINDEX_LINKAGE unsigned clang_Type_isTransparentTagTypedef(CXType T);
 
+enum CXTypeNullabilityKind {
+  /**
+   * Values of this type can never be null.
+   */
+  CXTypeNullability_NonNull = 0,
+  /**
+   * Values of this type can be null.
+   */
+  CXTypeNullability_Nullable = 1,
+  /**
+   * Whether values of this type can be null is (explicitly)
+   * unspecified. This captures a (fairly rare) case where we
+   * can't conclude anything about the nullability of the type even
+   * though it has been considered.
+   */
+  CXTypeNullability_Unspecified = 2,
+  /**
+   * Nullability is not applicable to this type.
+   */
+  CXTypeNullability_Invalid = 3
+};
+
+/**
+ * Retrieve the nullability kind of a pointer type.
+ */
+CINDEX_LINKAGE enum CXTypeNullabilityKind clang_Type_getNullability(CXType T);
+
 /**
  * List the possible error codes for \c clang_Type_getSizeOf,
  *   \c clang_Type_getAlignOf, \c clang_Type_getOffsetOf and

Added: cfe/trunk/test/Index/nullability.c
URL: http://llvm.org/viewvc/llvm-project/cfe/trunk/test/Index/nullability.c?rev=338809&view=auto
==============================================================================
--- cfe/trunk/test/Index/nullability.c (added)
+++ cfe/trunk/test/Index/nullability.c Thu Aug  2 21:38:04 2018
@@ -0,0 +1,10 @@
+int *a;
+int * _Nonnull b;
+int * _Nullable c;
+int * _Null_unspecified d;
+
+// RUN: env CINDEXTEST_INCLUDE_ATTRIBUTED_TYPES=1 c-index-test -test-print-type %s | FileCheck %s
+// CHECK: VarDecl=a:1:6 [type=int *] [typekind=Pointer] [isPOD=1] [pointeetype=int] [pointeekind=Int]
+// CHECK: VarDecl=b:2:16 [type=int * _Nonnull] [typekind=Attributed] [nullability=nonnull] [canonicaltype=int *] [canonicaltypekind=Pointer] [modifiedtype=int *] [modifiedtypekind=Pointer] [isPOD=1]
+// CHECK: VarDecl=c:3:17 [type=int * _Nullable] [typekind=Attributed] [nullability=nullable] [canonicaltype=int *] [canonicaltypekind=Pointer] [modifiedtype=int *] [modifiedtypekind=Pointer] [isPOD=1]
+// CHECK: VarDecl=d:4:25 [type=int * _Null_unspecified] [typekind=Attributed] [nullability=unspecified] [canonicaltype=int *] [canonicaltypekind=Pointer] [modifiedtype=int *] [modifiedtypekind=Pointer] [isPOD=1]

Modified: cfe/trunk/tools/c-index-test/c-index-test.c
URL: http://llvm.org/viewvc/llvm-project/cfe/trunk/tools/c-index-test/c-index-test.c?rev=338809&r1=338808&r2=338809&view=diff
==============================================================================
--- cfe/trunk/tools/c-index-test/c-index-test.c (original)
+++ cfe/trunk/tools/c-index-test/c-index-test.c Thu Aug  2 21:38:04 2018
@@ -84,6 +84,8 @@ static unsigned getDefaultParsingOptions
     options |= CXTranslationUnit_KeepGoing;
   if (getenv("CINDEXTEST_LIMIT_SKIP_FUNCTION_BODIES_TO_PREAMBLE"))
     options |= CXTranslationUnit_LimitSkipFunctionBodiesToPreamble;
+  if (getenv("CINDEXTEST_INCLUDE_ATTRIBUTED_TYPES"))
+    options |= CXTranslationUnit_IncludeAttributedTypes;
 
   return options;
 }
@@ -1496,6 +1498,22 @@ static void PrintTypeTemplateArgs(CXType
   }
 }
 
+static void PrintNullabilityKind(CXType T, const char *Format) {
+  enum CXTypeNullabilityKind N = clang_Type_getNullability(T);
+
+  const char *nullability = 0;
+  switch (N) {
+    case CXTypeNullability_NonNull: nullability = "nonnull"; break;
+    case CXTypeNullability_Nullable: nullability = "nullable"; break;
+    case CXTypeNullability_Unspecified: nullability = "unspecified"; break;
+    case CXTypeNullability_Invalid: break;
+  }
+
+  if (nullability) {
+    printf(Format, nullability);
+  }
+}
+
 static enum CXChildVisitResult PrintType(CXCursor cursor, CXCursor p,
                                          CXClientData d) {
   if (!clang_isInvalid(clang_getCursorKind(cursor))) {
@@ -1504,6 +1522,7 @@ static enum CXChildVisitResult PrintType
     enum CXRefQualifierKind RQ = clang_Type_getCXXRefQualifier(T);
     PrintCursor(cursor, NULL);
     PrintTypeAndTypeKind(T, " [type=%s] [typekind=%s]");
+    PrintNullabilityKind(T, " [nullability=%s]");
     if (clang_isConstQualifiedType(T))
       printf(" const");
     if (clang_isVolatileQualifiedType(T))
@@ -1524,12 +1543,20 @@ static enum CXChildVisitResult PrintType
         PrintTypeTemplateArgs(CT, " [canonicaltemplateargs/%d=");
       }
     }
+    /* Print the modified type if it exists. */
+    {
+      CXType MT = clang_Type_getModifiedType(T);
+      if (MT.kind != CXType_Invalid) {
+        PrintTypeAndTypeKind(MT, " [modifiedtype=%s] [modifiedtypekind=%s]");
+      }
+    }
     /* Print the return type if it exists. */
     {
       CXType RT = clang_getCursorResultType(cursor);
       if (RT.kind != CXType_Invalid) {
         PrintTypeAndTypeKind(RT, " [resulttype=%s] [resulttypekind=%s]");
       }
+      PrintNullabilityKind(RT, " [resultnullability=%s]");
     }
     /* Print the argument types if they exist. */
     {
@@ -1541,6 +1568,7 @@ static enum CXChildVisitResult PrintType
           CXType T = clang_getCursorType(clang_Cursor_getArgument(cursor, i));
           if (T.kind != CXType_Invalid) {
             PrintTypeAndTypeKind(T, " [%s] [%s]");
+            PrintNullabilityKind(T, " [%s]");
           }
         }
         printf("]");

Modified: cfe/trunk/tools/libclang/CXType.cpp
URL: http://llvm.org/viewvc/llvm-project/cfe/trunk/tools/libclang/CXType.cpp?rev=338809&r1=338808&r2=338809&view=diff
==============================================================================
--- cfe/trunk/tools/libclang/CXType.cpp (original)
+++ cfe/trunk/tools/libclang/CXType.cpp Thu Aug  2 21:38:04 2018
@@ -1240,3 +1240,22 @@ unsigned clang_Type_isTransparentTagType
   }
   return false;
 }
+
+enum CXTypeNullabilityKind clang_Type_getNullability(CXType CT) {
+  QualType T = GetQualType(CT);
+  if (T.isNull())
+    return CXTypeNullability_Invalid;
+
+  ASTContext &Ctx = cxtu::getASTUnit(GetTU(CT))->getASTContext();
+  if (auto nullability = T->getNullability(Ctx)) {
+    switch (*nullability) {
+      case NullabilityKind::NonNull:
+        return CXTypeNullability_NonNull;
+      case NullabilityKind::Nullable:
+        return CXTypeNullability_Nullable;
+      case NullabilityKind::Unspecified:
+        return CXTypeNullability_Unspecified;
+    }
+  }
+  return CXTypeNullability_Invalid;
+}

Modified: cfe/trunk/tools/libclang/libclang.exports
URL: http://llvm.org/viewvc/llvm-project/cfe/trunk/tools/libclang/libclang.exports?rev=338809&r1=338808&r2=338809&view=diff
==============================================================================
--- cfe/trunk/tools/libclang/libclang.exports (original)
+++ cfe/trunk/tools/libclang/libclang.exports Thu Aug  2 21:38:04 2018
@@ -104,6 +104,7 @@ clang_Type_getObjCProtocolDecl
 clang_Type_getNumObjCTypeArgs
 clang_Type_getObjCTypeArg
 clang_Type_getModifiedType
+clang_Type_getNullability
 clang_VerbatimBlockLineComment_getText
 clang_VerbatimLineComment_getText
 clang_HTMLTagComment_getAsString




More information about the cfe-commits mailing list