Class FindImproperSynchronization
java.lang.Object
edu.umd.cs.findbugs.visitclass.BetterVisitor
edu.umd.cs.findbugs.visitclass.PreorderVisitor
edu.umd.cs.findbugs.visitclass.AnnotationVisitor
edu.umd.cs.findbugs.visitclass.DismantleBytecode
edu.umd.cs.findbugs.BytecodeScanningDetector
edu.umd.cs.findbugs.bcel.OpcodeStackDetector
edu.umd.cs.findbugs.detect.FindImproperSynchronization
- All Implemented Interfaces:
Detector, Priorities, org.apache.bcel.classfile.Visitor
-
Nested Class Summary
Nested ClassesNested classes/interfaces inherited from class OpcodeStackDetector
OpcodeStackDetector.WithCustomJumpInfo -
Field Summary
FieldsModifier and TypeFieldDescriptionprivate final BugReporterprivate final MultiMap<XField, FindImproperSynchronization.BugInfo> private final MultiMap<XField, FindImproperSynchronization.BugInfo> private static final Map<MethodDescriptor, Integer> Fields inherited from class OpcodeStackDetector
stackFields inherited from class DismantleBytecode
codeBytes, lineNumberTable, M_BR, M_CP, M_INT, M_PAD, M_R, M_UINTFields inherited from interface Priorities
EXP_PRIORITY, HIGH_PRIORITY, IGNORE_PRIORITY, LOW_PRIORITY, NORMAL_PRIORITY -
Constructor Summary
Constructors -
Method Summary
Modifier and TypeMethodDescriptionprivate voidanalyzeAssignments(org.apache.bcel.classfile.Method obj, ClassContext classContext) private voidanalyzeAssignments(org.apache.bcel.classfile.Method obj, ClassContext classContext, XField specificField) private voidanalyzeAssignmentsInHierarchy(XField collectionLockObject) private voidanalyzeWrappedField(org.apache.bcel.classfile.Method currentMethod, ClassContext classContext, Location location, org.apache.bcel.generic.InstructionHandle handle, XField assignedField, Integer stackOffsetForWrapperMethodParameter) Analyze a wrapping method call and check if this the creation of a binding collection.private StringbuildMethodsMessage(Collection<XMethod> methods) private voidcheckLockUsageInHierarchy(XField field, XMethod exposingMethod) private voidfindExposureInHierarchy(XField lockObject) findLockUsageInHierarchy(XField field) private static IntegergetStackOffset(MethodDescriptor methodDescriptor) private booleanisCollection(XField field) private booleanisCollection(org.apache.bcel.generic.Type type) private static booleanisImmutableReturner(String signature) private booleanisInherited(XField lockObject) Check if the lock object is inherited from the current class.private booleanisInitializerMethod(String methodName) private booleanisMethodCall(org.apache.bcel.generic.Instruction instruction) private booleanisPackagePrivate(XField field) private static booleanisWrapperImplementation(MethodDescriptor methodDescriptor) private voidreportAccessibleBackingCollectionBug(XField lock, MultiMap<XField, FindImproperSynchronization.BugInfo> possibleBugs, XField backingCollection, MultiMap<XField, XMethod> collectionAccessors) private voidreportAccessibleObjectBug(XField lock, Collection<XMethod> definedLockAccessors, Map<XField, XMethod> synchronizedMethods) private voidreportBadCollectionObjectBugs(XField lock, MultiMap<XField, FindImproperSynchronization.BugInfo> possibleBugs, XField backingCollection) private voidreportExposingLockObjectBugs(XField lock, Collection<XMethod> lockUsingMethods, Collection<XMethod> exposingMethods) private voidreportInheritedBackingCollectionBug(XField lock, MultiMap<XField, FindImproperSynchronization.BugInfo> possibleBugs, XField backingCollection) private voidreportInheritedObjectBugs(XField lock, Collection<XMethod> synchronizedMethods) private voidreportObjectBugs(XField lock, Collection<XMethod> synchronizedMethods) voidsawOpcode(int seen) By default, this method will not be called when stack is TOP.voidvisit(org.apache.bcel.classfile.Field obj) voidvisit(org.apache.bcel.classfile.Method obj) voidvisitAfter(org.apache.bcel.classfile.JavaClass obj) Methods inherited from class OpcodeStackDetector
afterOpcode, beforeOpcode, getStack, isUsingCustomUserValue, visitCodeMethods inherited from class BytecodeScanningDetector
getClassContext, report, shouldVisitCode, visitClassContextMethods inherited from class DismantleBytecode
areOppositeBranches, atCatchBlock, getBranchFallThrough, getBranchOffset, getBranchTarget, getClassConstantOperand, getClassDescriptorOperand, getCodeByte, getConstantRefOperand, getDefaultSwitchOffset, getDottedClassConstantOperand, getFieldDescriptorOperand, getIntConstant, getLongConstant, getMaxPC, getMethodDescriptorOperand, getNameConstantOperand, getNextCodeByte, getNextOpcode, getNextPC, getOpcode, getPC, getPrevOpcode, getRefFieldIsStatic, getRegisterOperand, getSigConstantOperand, getStringConstantOperand, getSwitchLabels, getSwitchOffsets, getXClassOperand, getXFieldOperand, getXMethodOperand, isBranch, isIf, isMethodCall, isRegisterLoad, isRegisterStore, isRegisterStore, isReturn, isShift, isSwitch, isWideOpcode, normalizeNullComparison, printOpCode, sawBranchTo, sawClass, sawDouble, sawField, sawFloat, sawIMethod, sawInt, sawLong, sawMethod, sawRegister, sawString, visitMethods inherited from class AnnotationVisitor
getAnnotationParameterAsEnum, getAnnotationParameterAsString, getAnnotationParameterAsStringArray, visitAnnotation, visitAnnotation, visitParameterAnnotation, visitParameterAnnotation, visitSyntheticParameterAnnotationMethods inherited from class PreorderVisitor
amVisitingMainMethod, asUnsignedByte, doVisitMethod, getClassDescriptor, getClassName, getCode, getConstantPool, getDottedClassName, getDottedMethodSig, getDottedSuperclassName, getField, getFieldDescriptor, getFieldIsStatic, getFieldName, getFieldSig, getFullyQualifiedFieldName, getFullyQualifiedMethodName, getMethod, getMethodDescriptor, getMethodName, getMethodSig, getMethodVisitOrder, getNumberArguments, getNumberMethodArguments, getPackageName, getSizeOfSurroundingTryBlock, getSizeOfSurroundingTryBlock, getSourceFile, getStringFromIndex, getSuperclassName, getSurroundingCaughtExceptions, getSurroundingCaughtExceptions, getSurroundingCaughtExceptionTypes, getSurroundingTryBlock, getSurroundingTryBlock, getThisClass, getXClass, getXField, getXMethod, hasInterestingClass, hasInterestingMethod, isVisitMethodsInCallOrder, setupVisitorForClass, setVisitMethodsInCallOrder, shouldVisit, toString, visitAfter, visitAnnotationDefault, visitAnnotationEntry, visitBootstrapMethods, visitConstantInvokeDynamic, visitConstantMethodHandle, visitConstantMethodType, visitConstantModule, visitConstantPackage, visitConstantPool, visitEnclosingMethod, visitingField, visitingMethod, visitInnerClasses, visitJavaClass, visitLineNumberTable, visitLocalVariableTable, visitMethodParameters, visitParameterAnnotationEntry, visitStackMap, visitStackMapEntryMethods inherited from class BetterVisitor
clone, report, visit, visit, visit, visit, visit, visit, visit, visit, visit, visit, visit, visit, visit, visit, visit, visit, visit, visit, visit, visit, visit, visit, visit, visit, visit, visit, visit, visit, visit, visit, visit, visit, visitCodeException, visitConstantClass, visitConstantDouble, visitConstantFieldref, visitConstantFloat, visitConstantInteger, visitConstantInterfaceMethodref, visitConstantLong, visitConstantMethodref, visitConstantNameAndType, visitConstantString, visitConstantUtf8, visitConstantValue, visitDeprecated, visitExceptionTable, visitField, visitInnerClass, visitLineNumber, visitLocalVariable, visitLocalVariableTypeTable, visitMethod, visitSignature, visitSourceFile, visitSynthetic, visitUnknownMethods inherited from class Object
equals, finalize, getClass, hashCode, notify, notifyAll, wait, wait, waitMethods inherited from interface org.apache.bcel.classfile.Visitor
visitConstantDynamic, visitMethodParameter, visitModule, visitModuleExports, visitModuleMainClass, visitModuleOpens, visitModulePackages, visitModuleProvides, visitModuleRequires, visitNestHost, visitNestMembers, visitRecord, visitRecordComponent, visitStackMapType
-
Field Details
-
WRAPPER_IMPLEMENTATIONS
-
IMMUTABLE_RETURNERS
-
bugReporter
-
exposingMethods
-
synchronizedMethods
-
declaredLockObjects
-
inheritedLockObjects
-
declaredLockAccessors
-
lockAccessorsInHierarchy
-
lockUsingMethodsInHierarchy
-
declaredInheritedFieldAccessingMethods
-
potentialObjectBugContainingMethods
-
potentialInheritedBugContainingMethods
-
badBackingCollections
-
inheritableBackingCollections
-
declaredCollectionLockObjects
-
inheritedCollectionLockObjects
-
declaredCollectionAccessors
-
collectionAccessorsInHierarchy
-
backingCollections
-
-
Constructor Details
-
FindImproperSynchronization
-
-
Method Details
-
isWrapperImplementation
-
getStackOffset
-
isImmutableReturner
-
visit
public void visit(org.apache.bcel.classfile.Method obj) - Overrides:
visitin classBetterVisitor
-
visit
public void visit(org.apache.bcel.classfile.Field obj) - Overrides:
visitin classBetterVisitor
-
sawOpcode
public void sawOpcode(int seen) Description copied from class:OpcodeStackDetectorBy default, this method will not be called when stack is TOP. To change this behavior, override
#beforeOpcode(int)and change to return true even if stack is TOP.see Using FindBugs for Research to learn lattice and what TOP means.
- Specified by:
sawOpcodein classOpcodeStackDetector- See Also:
-
visitAfter
public void visitAfter(org.apache.bcel.classfile.JavaClass obj) - Overrides:
visitAfterin classPreorderVisitor
-
isCollection
private boolean isCollection(org.apache.bcel.generic.Type type) -
isCollection
-
isMethodCall
private boolean isMethodCall(org.apache.bcel.generic.Instruction instruction) -
isPackagePrivate
-
isInitializerMethod
-
isInherited
Check if the lock object is inherited from the current class. To ensure no false positives, we compare only the outer class name if the lock object is contained in an inner class. Only checking equality is enough, since the lock object is a field declared in a class. That means if the declaring class of the lock object is the same as the current class, the lock object is not inherited.- Parameters:
lockObject- the lock object to check for inheritance- Returns:
- true if the lock object is inherited from the current class, false otherwise
-
analyzeWrappedField
private void analyzeWrappedField(org.apache.bcel.classfile.Method currentMethod, ClassContext classContext, Location location, org.apache.bcel.generic.InstructionHandle handle, XField assignedField, Integer stackOffsetForWrapperMethodParameter) Analyze a wrapping method call and check if this the creation of a binding collection. There are specific methods that use their parameters to create a new collections, but they maintain a reference to the original collection. When a collection is wrapped by such a method and the result is assigned to a field, the wrapped collections becomes a backing collection.- Parameters:
currentMethod- the method in which the wrapping method call is locatedclassContext- the class context of the currently analyzed class, in which the wrapping method call is locatedlocation- the location of the wrapping method callhandle- the instruction handle of the wrapping method callassignedField- the field to which the result of the wrapping method call is assignedstackOffsetForWrapperMethodParameter- the stack offset of the wrapped collection parameter of the wrapping method call
-
analyzeAssignments
private void analyzeAssignments(org.apache.bcel.classfile.Method obj, ClassContext classContext) throws CFGBuilderException - Throws:
CFGBuilderException
-
analyzeAssignments
private void analyzeAssignments(org.apache.bcel.classfile.Method obj, ClassContext classContext, XField specificField) throws CFGBuilderException - Throws:
CFGBuilderException
-
analyzeAssignmentsInHierarchy
-
checkLockUsageInHierarchy
-
findExposureInHierarchy
- Throws:
ClassNotFoundException
-
findLockUsageInHierarchy
- Throws:
ClassNotFoundException
-
buildMethodsMessage
-
reportExposingLockObjectBugs
private void reportExposingLockObjectBugs(XField lock, Collection<XMethod> lockUsingMethods, Collection<XMethod> exposingMethods) -
reportAccessibleObjectBug
-
reportInheritedObjectBugs
-
reportObjectBugs
-
reportAccessibleBackingCollectionBug
-
reportInheritedBackingCollectionBug
private void reportInheritedBackingCollectionBug(XField lock, MultiMap<XField, FindImproperSynchronization.BugInfo> possibleBugs, XField backingCollection) -
reportBadCollectionObjectBugs
private void reportBadCollectionObjectBugs(XField lock, MultiMap<XField, FindImproperSynchronization.BugInfo> possibleBugs, XField backingCollection) -
clearState
private void clearState()
-