added TODOs to report wip
This commit is contained in:
parent
2a35025e5a
commit
9511c2303d
4 changed files with 52 additions and 26 deletions
|
@ -120,16 +120,11 @@ public static Field getField(final Class<?> cls, final String fieldName, final b
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
final List<Class<?>> interfaces = ClassUtils.getAllInterfaces(cls);
|
|
||||||
if (interfaces == null) {
|
|
||||||
return null;
|
|
||||||
}
|
|
||||||
|
|
||||||
// check the public interface case. This must be manually searched for
|
// check the public interface case. This must be manually searched for
|
||||||
// incase there is a public supersuperclass field hidden by a private/package
|
// incase there is a public supersuperclass field hidden by a private/package
|
||||||
// superclass field.
|
// superclass field.
|
||||||
Field match = null;
|
Field match = null;
|
||||||
for (final Class<?> class1 : interfaces) {
|
for (final Class<?> class1 : ClassUtils.getAllInterfaces(cls)) {
|
||||||
try {
|
try {
|
||||||
final Field test = class1.getField(fieldName);
|
final Field test = class1.getField(fieldName);
|
||||||
Validate.isTrue(match == null, "Reference to field %s is ambiguous relative to %s"
|
Validate.isTrue(match == null, "Reference to field %s is ambiguous relative to %s"
|
||||||
|
|
|
@ -476,7 +476,7 @@ static Object[] getVarArgs(final Object[] args, final Class<?>[] methodParameter
|
||||||
final int varArgLength = args.length - methodParameterTypes.length + 1;
|
final int varArgLength = args.length - methodParameterTypes.length + 1;
|
||||||
|
|
||||||
if (varArgComponentType == null) {
|
if (varArgComponentType == null) {
|
||||||
throw new NullPointerException("last method parameter type is not an array");
|
throw new IllegalArgumentException("last method parameter type is not an array");
|
||||||
}
|
}
|
||||||
|
|
||||||
Object varArgsArray = Array.newInstance(ClassUtils.primitiveToWrapper(varArgComponentType), varArgLength);
|
Object varArgsArray = Array.newInstance(ClassUtils.primitiveToWrapper(varArgComponentType), varArgLength);
|
||||||
|
|
BIN
report.pdf
BIN
report.pdf
Binary file not shown.
69
report.tex
69
report.tex
|
@ -56,7 +56,7 @@
|
||||||
\geometry{left=2cm,right=2cm,top=2cm,bottom=3cm}
|
\geometry{left=2cm,right=2cm,top=2cm,bottom=3cm}
|
||||||
\title{
|
\title{
|
||||||
\vspace{-5ex}
|
\vspace{-5ex}
|
||||||
Assignment 1 -- Software Analysis \\\vspace{0.5cm}
|
Assignment 2 -- Software Analysis \\\vspace{0.5cm}
|
||||||
\Large Static Analysis with Infer
|
\Large Static Analysis with Infer
|
||||||
\vspace{-1ex}
|
\vspace{-1ex}
|
||||||
}
|
}
|
||||||
|
@ -136,15 +136,12 @@ on \textit{gitlab.com}. The script \textit{docker-infer.sh} can be executed to
|
||||||
automatically run the Infer tool using default options through the course
|
automatically run the Infer tool using default options through the course
|
||||||
tools docker image \textit{bugcounting/satools:y23}.
|
tools docker image \textit{bugcounting/satools:y23}.
|
||||||
|
|
||||||
The script selects Java 17 to compile the project as this is required to not
|
|
||||||
make the Animal Sniffer Maven build plugin fail with the message ``This feature
|
|
||||||
requires ASM7''.
|
|
||||||
|
|
||||||
The script executes Infer in Maven capture mode executing the \textit{compile}
|
The script executes Infer in Maven capture mode executing the \textit{compile}
|
||||||
and \textit{test} targets while disabling the Apache RAT software license
|
and \textit{test} targets while disabling the Apache RAT software license
|
||||||
checker (which fails for this release). Since unit tests are executed, running
|
checker (which fails for this release) and the Animal Sniffer Maven plugin do to
|
||||||
the script before and after the warning guided refactoring ensures the fixes I
|
the failure message ``This feature requires ASM7'' it produces if ran. Since
|
||||||
introduce do not introduce regressions.
|
unit tests are executed, running the script before and after the warning guided
|
||||||
|
refactoring ensures the fixes I introduce do not introduce regressions.
|
||||||
|
|
||||||
The analysis outputs
|
The analysis outputs
|
||||||
are located in \textit{before/infer-out/report.txt}.
|
are located in \textit{before/infer-out/report.txt}.
|
||||||
|
@ -161,8 +158,7 @@ result.
|
||||||
\toprule
|
\toprule
|
||||||
\textbf{File} & \textbf{Line} & \textbf{Kind} & \textbf{True Pos.} &
|
\textbf{File} & \textbf{Line} & \textbf{Kind} & \textbf{True Pos.} &
|
||||||
\textbf{Reason why flagged expression is a false positive} \\ \midrule
|
\textbf{Reason why flagged expression is a false positive} \\ \midrule
|
||||||
AnnotationUtils.java & 72 & Null & Yes & \multirow{4}{6cm}{--} \\
|
AnnotationUtils.java & 72 & Null & Yes & \\
|
||||||
reflect/MethodUtils.java & 486 & Null & Yes & \\
|
|
||||||
reflect/FieldUtils.java & 126 & Null & Yes & \\
|
reflect/FieldUtils.java & 126 & Null & Yes & \\
|
||||||
concurrent/MultiBackgroundInitializer.java & 160 & Thread Safety & Yes & \\
|
concurrent/MultiBackgroundInitializer.java & 160 & Thread Safety & Yes & \\
|
||||||
\midrule
|
\midrule
|
||||||
|
@ -170,9 +166,11 @@ builder/ToStringBuilder.java & 223 & Null & No & \multirow{2}{6cm}{Infer flags
|
||||||
the value \texttt{null} when used as a nullable method argument} \\
|
the value \texttt{null} when used as a nullable method argument} \\
|
||||||
builder/ReflectionToStringBuilder.java & 131 & Null & No & \\
|
builder/ReflectionToStringBuilder.java & 131 & Null & No & \\
|
||||||
\midrule
|
\midrule
|
||||||
time/DurationUtils.java & 142 & Null & No & The method which may return a null
|
time/DurationUtils.java & 142 & Null & No & \multirow{3}{6.2cm}{The method which
|
||||||
value returns a non-null value if its parameter is non-null, and a
|
may return a null value returns a non-null value if its parameter is
|
||||||
non-null parameter is given \\
|
non-null, and a non-null parameter is given} \\
|
||||||
|
reflect/MethodUtils.java & 486 & Null & No & \\
|
||||||
|
\\ \hspace{1cm} \\
|
||||||
\midrule
|
\midrule
|
||||||
CharSetUtils.java & 181 & Null & No & According to \textit{java.lang}
|
CharSetUtils.java & 181 & Null & No & According to \textit{java.lang}
|
||||||
documentation, the method always returns a non-null value \\
|
documentation, the method always returns a non-null value \\
|
||||||
|
@ -197,9 +195,9 @@ documentation for the inner nested method \\ \bottomrule
|
||||||
\end{table}
|
\end{table}
|
||||||
|
|
||||||
In total Infer reports 13 warnings, 12 of which are null dereference warnings
|
In total Infer reports 13 warnings, 12 of which are null dereference warnings
|
||||||
and 1 is a thread safety violation. Of all warnings, 4 are true positives and 9
|
and 1 is a thread safety violation. Of all warnings, 3 are true positives and 10
|
||||||
are false positives, resulting in a false positive ratio of over 69\%. These
|
are false positives, resulting in a precision of 23\%.
|
||||||
values are summarized in table \ref{tab:num}.
|
These values are summarized in table \ref{tab:num}.
|
||||||
|
|
||||||
\begin{table}[H]
|
\begin{table}[H]
|
||||||
\centering
|
\centering
|
||||||
|
@ -208,8 +206,8 @@ values are summarized in table \ref{tab:num}.
|
||||||
Total number of warnings: & 13 \\ \midrule
|
Total number of warnings: & 13 \\ \midrule
|
||||||
Null dereference warnings: & 12 \\
|
Null dereference warnings: & 12 \\
|
||||||
Thread safety violations: & 1 \\ \midrule
|
Thread safety violations: & 1 \\ \midrule
|
||||||
True positives: & 4 \\
|
True positives: & 3 \\
|
||||||
False positives: & 9 \\ \bottomrule
|
False positives: & 10 \\ \bottomrule
|
||||||
\end{tabular}
|
\end{tabular}
|
||||||
\caption{Quantitative results of the static analysis performed by Infer.}
|
\caption{Quantitative results of the static analysis performed by Infer.}
|
||||||
\label{tab:num}
|
\label{tab:num}
|
||||||
|
@ -226,7 +224,8 @@ In other cases, the flagged expression is guarded by an utility method throwing
|
||||||
an exception if its value is indeed \texttt{null}. One of such guards is the
|
an exception if its value is indeed \texttt{null}. One of such guards is the
|
||||||
\mintinline{java}{static Validate.notNull(Object, String, Object...)} method,
|
\mintinline{java}{static Validate.notNull(Object, String, Object...)} method,
|
||||||
which checks if its first argument is null and throws a
|
which checks if its first argument is null and throws a
|
||||||
\texttt{NullPointerException} if so.
|
\texttt{NullPointerException} with a ``pretty'' message composed from a format
|
||||||
|
string and variadic arguments if so.
|
||||||
|
|
||||||
Additionally, Infer seems to struggle with boxed primitives and not
|
Additionally, Infer seems to struggle with boxed primitives and not
|
||||||
understanding that their value is always non-null by construction. As an example
|
understanding that their value is always non-null by construction. As an example
|
||||||
|
@ -280,5 +279,37 @@ causing null dereferences.
|
||||||
In this section I now cover the warnings that are true positives and thus are
|
In this section I now cover the warnings that are true positives and thus are
|
||||||
causes for refactoring.
|
causes for refactoring.
|
||||||
|
|
||||||
|
\begin{center}
|
||||||
|
\color{red}
|
||||||
|
- field utils violation of contract
|
||||||
|
|
||||||
|
- missing synchronized in multibackground
|
||||||
|
|
||||||
|
- Annotation utils protected method no contract on field fixed by returning
|
||||||
|
"empty" value
|
||||||
|
|
||||||
|
- no additional warnings appear after fix
|
||||||
|
|
||||||
|
- cool that a contract violation has been found
|
||||||
|
|
||||||
|
- tests pass after fixes so no regression
|
||||||
|
\end{center}
|
||||||
|
|
||||||
|
\section{Conclusions}
|
||||||
|
|
||||||
|
\begin{center}
|
||||||
|
\color{red}
|
||||||
|
- project is mature, few detections but still a couple for null values which
|
||||||
|
shows how insidious they are. (Null and thread safety are popular and
|
||||||
|
relevant to the project)
|
||||||
|
|
||||||
|
- infer compared to pmd gives warnings about potential execution paths (data
|
||||||
|
flow analysis) while pmd is style only and bound to the language
|
||||||
|
|
||||||
|
- sonarqube kind of covers some ground infer does. it combines the powers of
|
||||||
|
pmd (patterns common to the language to avoid/pursue) with some data flow
|
||||||
|
analysis (some nullability check). No overlap with Infer results
|
||||||
|
\end{center}
|
||||||
|
|
||||||
\end{document}
|
\end{document}
|
||||||
|
|
||||||
|
|
Reference in a new issue