tree: c950438ac780e324747418a94ded5291f304c15d
  1. annotatedBoundsOfWildcard/
  2. defaults/
  3. fullyQualified/
  4. ignoreAnnotations/
  5. nonPlatformTypeParameter/
  6. nullnessUnspecifiedTypeParameter/
  7. packageDefault/
  8. selfType/
  9. simple/
  10. typeArgumentsFromParameterBounds/
  11. typeParameterBounds/
  12. wildcardsWithDefault/
  13. AnnotatedInnerOfNonParameterized.java
  14. AnnotatedInnerOfParameterized.java
  15. AnnotatedReceiver.java
  16. AnnotatedTypeParameter.java
  17. AnnotatedTypeParameterUnspec.java
  18. AnnotatedWildcard.java
  19. AnnotatedWildcardUnspec.java
  20. AssignmentAsExpression.java
  21. AugmentedInferenceAgreesWithBaseInference.java
  22. BoundedTypeVariableReturn.java
  23. CaptureConversionForSubtyping.java
  24. CaptureConvertedToObject.java
  25. CaptureConvertedToObjectUnionNull.java
  26. CaptureConvertedToObjectUnspec.java
  27. CaptureConvertedToOther.java
  28. CaptureConvertedToOtherUnionNull.java
  29. CaptureConvertedToOtherUnspec.java
  30. CaptureConvertedUnionNullToObject.java
  31. CaptureConvertedUnionNullToObjectUnionNull.java
  32. CaptureConvertedUnionNullToObjectUnspec.java
  33. CaptureConvertedUnionNullToOther.java
  34. CaptureConvertedUnionNullToOtherUnionNull.java
  35. CaptureConvertedUnionNullToOtherUnspec.java
  36. CaptureConvertedUnspecToObject.java
  37. CaptureConvertedUnspecToObjectUnionNull.java
  38. CaptureConvertedUnspecToObjectUnspec.java
  39. CaptureConvertedUnspecToOther.java
  40. CaptureConvertedUnspecToOtherUnionNull.java
  41. CaptureConvertedUnspecToOtherUnspec.java
  42. CastToPrimitive.java
  43. Catch.java
  44. ClassLiteral.java
  45. ClassToObject.java
  46. ClassToSelf.java
  47. ComplexParametric.java
  48. ConcatResult.java
  49. ConflictingAnnotations.java
  50. Constants.java
  51. ContainmentExtends.java
  52. ContainmentSuper.java
  53. ContainmentSuperVsExtends.java
  54. ContravariantReturns.java
  55. CovariantReturns.java
  56. DereferenceClass.java
  57. DereferenceIntersection.java
  58. DereferenceTypeVariable.java
  59. EnumAnnotations.java
  60. IfCondition.java
  61. InferenceChoosesNullableTypeVariable.java
  62. InstanceOfCheck.java
  63. InstanceOfMethodCheck.java
  64. IntersectionSupertype.java
  65. LocalVariable.java
  66. MultiBoundTypeVariableToObject.java
  67. MultiBoundTypeVariableToObjectUnionNull.java
  68. MultiBoundTypeVariableToObjectUnspec.java
  69. MultiBoundTypeVariableToOther.java
  70. MultiBoundTypeVariableToOtherUnionNull.java
  71. MultiBoundTypeVariableToOtherUnspec.java
  72. MultiBoundTypeVariableToSelf.java
  73. MultiBoundTypeVariableToSelfUnionNull.java
  74. MultiBoundTypeVariableToSelfUnspec.java
  75. MultiBoundTypeVariableUnionNullToObject.java
  76. MultiBoundTypeVariableUnionNullToObjectUnionNull.java
  77. MultiBoundTypeVariableUnionNullToObjectUnspec.java
  78. MultiBoundTypeVariableUnionNullToOther.java
  79. MultiBoundTypeVariableUnionNullToOtherUnionNull.java
  80. MultiBoundTypeVariableUnionNullToOtherUnspec.java
  81. MultiBoundTypeVariableUnionNullToSelf.java
  82. MultiBoundTypeVariableUnionNullToSelfUnionNull.java
  83. MultiBoundTypeVariableUnionNullToSelfUnspec.java
  84. MultiBoundTypeVariableUnspecToObject.java
  85. MultiBoundTypeVariableUnspecToObjectUnionNull.java
  86. MultiBoundTypeVariableUnspecToObjectUnspec.java
  87. MultiBoundTypeVariableUnspecToOther.java
  88. MultiBoundTypeVariableUnspecToOtherUnionNull.java
  89. MultiBoundTypeVariableUnspecToOtherUnspec.java
  90. MultiBoundTypeVariableUnspecToSelf.java
  91. MultiBoundTypeVariableUnspecToSelfUnionNull.java
  92. MultiBoundTypeVariableUnspecToSelfUnspec.java
  93. MultiplePathsToTypeVariable.java
  94. NonConstantPrimitives.java
  95. NotNullAwareAnnotatedInnerOfNonParameterized.java
  96. NotNullAwareAnnotatedInnerOfParameterized.java
  97. NotNullAwareAnnotatedTypeParameter.java
  98. NotNullAwareAnnotatedTypeParameterUnspec.java
  99. NotNullAwareAnnotatedWildcard.java
  100. NotNullAwareAnnotatedWildcardUnspec.java
  101. NotNullAwareClassToSelf.java
  102. NotNullAwareConcatResult.java
  103. NotNullAwareContainmentExtends.java
  104. NotNullAwareContainmentSuper.java
  105. NotNullAwareContainmentSuperVsExtends.java
  106. NotNullAwareIfCondition.java
  107. NotNullAwareInferenceChoosesNullableTypeVariable.java
  108. NotNullAwareLocalVariable.java
  109. NotNullAwareOverrides.java
  110. NotNullAwareTypeVariableBound.java
  111. NotNullAwareUnboxing.java
  112. NotNullAwareUseOfTypeVariable.java
  113. NotNullAwareUseOfTypeVariableAsTypeArgument.java
  114. NotNullAwareUseOfWildcardAsTypeArgument.java
  115. NullAwareDirectUseOfNotNullAwareBoundedTypeVariable.java
  116. NullCheck.java
  117. NullCheckTypeVariable.java
  118. NullCheckTypeVariableUnionNullBound.java
  119. NullCheckTypeVariableUnspecBound.java
  120. NullLiteralToClass.java
  121. NullLiteralToTypeVariable.java
  122. NullLiteralToTypeVariableUnionNull.java
  123. NullLiteralToTypeVariableUnspec.java
  124. NullnessDoesNotAffectOverloadSelection.java
  125. OverrideParameters.java
  126. OverrideParametersThatAreTypeVariables.java
  127. OverrideReturns.java
  128. ParameterizedWithTypeVariableArgumentToSelf.java
  129. PrimitiveAnnotations.java
  130. PrimitiveAnnotationsUnspec.java
  131. README.md
  132. SameTypeObject.java
  133. SameTypeTypeVariable.java
  134. SuperObject.java
  135. SuperObjectUnionNull.java
  136. SuperObjectUnspec.java
  137. SuperTypeVariable.java
  138. SuperTypeVariableUnionNull.java
  139. SuperTypeVariableUnspec.java
  140. Ternary.java
  141. TypeArgumentOfTypeVariableBound.java
  142. TypeArgumentOfWildcardBound.java
  143. TypeVariableToObject.java
  144. TypeVariableToObjectUnionNull.java
  145. TypeVariableToObjectUnspec.java
  146. TypeVariableToParent.java
  147. TypeVariableToParentUnionNull.java
  148. TypeVariableToParentUnspec.java
  149. TypeVariableToSelf.java
  150. TypeVariableToSelfUnionNull.java
  151. TypeVariableToSelfUnspec.java
  152. TypeVariableUnionNullToObject.java
  153. TypeVariableUnionNullToObjectUnionNull.java
  154. TypeVariableUnionNullToObjectUnspec.java
  155. TypeVariableUnionNullToParent.java
  156. TypeVariableUnionNullToParentUnionNull.java
  157. TypeVariableUnionNullToParentUnspec.java
  158. TypeVariableUnionNullToSelf.java
  159. TypeVariableUnionNullToSelfUnionNull.java
  160. TypeVariableUnionNullToSelfUnspec.java
  161. TypeVariableUnspecToObject.java
  162. TypeVariableUnspecToObjectUnionNull.java
  163. TypeVariableUnspecToObjectUnspec.java
  164. TypeVariableUnspecToParent.java
  165. TypeVariableUnspecToParentUnionNull.java
  166. TypeVariableUnspecToParentUnspec.java
  167. TypeVariableUnspecToSelf.java
  168. TypeVariableUnspecToSelfUnionNull.java
  169. TypeVariableUnspecToSelfUnspec.java
  170. Unboxing.java
  171. UninitializedField.java
  172. UnionTypeArgumentWithUseSite.java
  173. UnrecognizedLocationsMisc.java
  174. UnspecifiedTypeArgumentForNonNullableParameter.java
  175. UseOfTypeVariableAsTypeArgument.java
  176. UseOfTypeVariableUnionNullAsTypeArgument.java
  177. UseOfTypeVariableUnspecAsTypeArgument.java
samples/README.md

Sample inputs

Disclaimers

These sample inputs are an experiment.

They use annotations whose names and meanings are not finalized.

They have not been code reviewed.

We do not know if this is even the format that we want our sample inputs to be in.

Whatever our final samples look like, we do not expect to present them as “conformance tests” that require any behavior from tools: The goal of our project is to provide one source of nullness information. Tools may use some, all, or none of that information. They may also use information from other sources. Based on the information they have available for any given piece of code, tools always have the option to issue a warning / error / other diagnostic for that code, and they always have the option not to.

The hope is that samples like these may be useful to those who wish to discuss the spec or implement tools. To that end, we welcome comments on both the format of these files and their content.

Directory structure

See jspecify: test-data format: Directory structure. TODO(#134): Inline that here if Tagir can sign the CLA and contribute it.

Additionally:

Fully qualified class names must be unique across all directories.

This permits all files to be compiled in a single tool invocation.

TODO: Consider requiring that all individual-file samples be in the top-level directory.

Each file must contain a single top-level class. TODO(#133): Consider relaxing this.

TODO: Consider requiring a file's path to match its package and class:

  • individual-file samples: Foo.java for Foo

  • full-directory samples: sampleFoo/Foo.java for Foo, sampleFoo/bar/Foo.java for bar.Foo

  • We may need additional accommodations for JPMS support to demonstrate module-level defaulting.

Restrictions

Files must be UTF-8 encoded.

Files must contain only printable ASCII characters and \n.

Files must be compatible with Java 8. TODO(#131): Decide how to label files that require a higher version so that we can allow them. (But still encourage sticking to Java 8 except for tests that specifically exercise newer features.)

Files must compile without error using stock javac.

Files must not depend on any classes other than the JSpecify annotations. This includes the Java platform APIs. Exception: Files may use java.lang.Object, but they still must not use its methods.

For example, files may use Object as a bound, parameter, or return type.

Files should avoid depending on the presence of absence of “smart” checker features, such as:

  • looking inside the body of a method to determine what parameters it dereferences or what it returns

    • To that end, prefer abstract methods when practical.
  • flow-sensitive typing

We also encourage writing files that demonstrate individual behaviors in isolation. For example, we encourage writing files to minimize how much they rely on type inference -- except, of course, for any files explicitly intended to demonstrate type inference.

What sample inputs demonstrate

Sample inputs demonstrate 2 cases:

  1. JSpecify annotations are applied in a way that is structurally illegal.

  2. The second case is more nuanced: Based on JSpecify annotations and rules, the code‘s types can all be augmented with nullness information. We could then apply normal JLS rules to those types. (For example, the value of a return statement must be convertible to the method’s return type.) We could adapt those rules to use JSpecify rules for subtyping. Based on that, we could identify type checks that would fail. (For example, return null in a method that must return a non-nullable type.)

Syntax

We define a format for Java comments to identify code that demonstrates the cases above.

A comment on a given line provides information about the following line.

Such a comment contains one of 5 special sequences. The first 3 cover case 1 from above:

  • jspecify_conflicting_annotations: for cases like @Nullable @NullnessUnspecified Foo

  • jspecify_unrecognized_location: for cases like class @Nullable Foo {}, in which JSpecify does not currently specify meaning for annotations on a given location but we can imagine uses for them

  • jspecify_nullness_intrinsically_not_nullable: for cases like @Nullable int

The remaining 2 cover case 2:

  • jspecify_nullness_mismatch: for certain instances of case 2

  • jspecify_nullness_not_enough_information: for certain instances of case 2

The difference between the “mismatch” and “not enough information” cases arises from unspecified nullness. The rough idea is that a type with unspecified nullness means: “When this code is annotated for nullness, either the type should have @Nullable on it, or it shouldn't.”

  • In a “mismatch,” the type check described above would fail no matter how the unspecified types are eventually annotated. (This is trivially the case whenever a failing type check involves no unspecified types.)

  • In a “not enough information,” there is at least one way that the unspecified types could be annotated that would fail the type checks, and there is at least one way that the unspecified types could be annotated that would pass the type checks.

Another way to look at it is how tools are likely (but not obligated!) to behave:

  • For “mismatch,” all tools are likely to report an error. (This assumes that a tool implements a given type check: For example, if a tool doesn‘t check type arguments at all, then naturally it wouldn’t report errors for them)

  • For “not enough information,” tools might not report anything, or they might report a warning, or they might report an error. We've sometimes spoken of these different behaviors as the difference between a “strict mode” and a “lenient mode.”

TODO: Consider additional features:

  • multiline comments
  • other locations for comments
  • multiple findings per line/comment
  • comments that apply to larger ranges -- possibly to syntax elements (like statements) rather than lines
  • comments that apply only to a particular part of the line

More TODOs

TODO: Consider how to map between samples and related GitHub issues (comments, filenames?).