Eclipse findbugs找出的bug案例说明

说明:1.Bug是findbug Eclipse插件原生的bug信息描述,Confidence 是fingbug团队认为该代码导致bug的可能性。

2.以下都是我使用findbug在公司项目中找到的一些bug,这里做一些中文的简短说明(不是翻译)

3.篇幅可能会有点长,阅读时,大家可以通过ctrl+f根据关键字查找自己相关的bug

BUG-0001

Bug: Field only ever set to null: com.bettersoft.admin.BtCorpManager.ps

All writes to this field are of the constant value null, and thus all reads of the field will return null. Check for errors, or remove it if it is useless.

Confidence: Normal, Rank: Troubling (12)

Pattern: UWF_NULL_FIELD

Type: UwF, Category: CORRECTNESS (Correctness)

代码片段:

?


1

2

3

4

5

6

7

8

9

10

public

class

BtCorpManager {

    private

BtCorp btcorp=
null;

    private

Connection con =
null;

    private

Statement st =
null;

    private

PreparedStatement ps =
null;

    private

ResultSet rs =
null;

    private

void

setConnection(String centerno)
throws

Exception{

        //con
= DBManager.getConnection(centerno);

        con
= DBManager.getConnection();

    }

解释说明:在BtCorpManager类里面定了一个私有的成员变量PreparedStatement ps,但是这个成员变量ps在实例范围内没有得到任何的初始化(采用默认的构造方法),始终为null,所以在实例范围内使用该成员变量时,如果不先对其进行初始化操作或者无意识的行为忘了初始化操作,那肯定是要报空指针异常,所以这无疑是一个bug

推荐修改: 自己看着办

BUG-0002

Bug: Nullcheck of form at line 36 of value previously dereferenced in com.bettersoft.admin.CorpEditAction.execute(ActionMapping, ActionForm, HttpServletRequest, HttpServletResponse)

A value is checked here to see whether it is null, but this value can‘t be null because it was previously dereferenced and if it were null a null pointer exception would have occurred at the earlier dereference. Essentially, this code and the previous dereference
disagree as to whether this value is allowed to be null. Either the check is redundant or the previous dereference is erroneous.

Confidence: High, Rank: Scary (9)

Pattern: RCN_REDUNDANT_NULLCHECK_WOULD_HAVE_BEEN_A_NPE

Type: RCN, Category: CORRECTNESS (Correctness)

代码片段:

?


1

2

3

4

5

6

7

8

9

10

11

12

13

14

15

16

public

ActionForward execute(ActionMapping mapping, ActionForm form, HttpServletRequest request, HttpServletResponse response)
throws

Exception {

        //throw
new UnsupportedOperationException("Method is not implemented");

        ActionErrors
errors =
new

ActionErrors();

        CreateCorpActionForm
createCorp =
new

CreateCorpActionForm();

        createCorp
= (CreateCorpActionForm)form;

        

        

        CreateCorpActionForm
webcorp=
new

CreateCorpActionForm();

        BudgetWebcorpManager
budgetWebcorpManager=
new

BudgetWebcorpManager();

        webcorp=budgetWebcorpManager.getCWebcorp(createCorp.getId());

        createCorp.setFbsaddapproveid(webcorp.getFbsaddapproveid());

        createCorp.setFbsinputapproveid(webcorp.getFbsinputapproveid());

        createCorp.setFbsprocessapproveid(webcorp.getFbsprocessapproveid());

        boolean

b=
false;

        if(createCorp!=null){

解释说明:注意到有个局部变量 CreateCorpActionForm
createCorp;再看下它的初始化过程,先是通过new给它分配了内存空间,紧接着有让它引用了了另一个未知的变量,这里说未知是指这个新的引用可能为空,显然 createCorp有可能指向一个空的地址,所以在接下来的引用中极可能报空指针异常(在引用之前不进行判空操作的话)! 在接下来的代码,如下

?


1

if(createCorp!=null){

其实也就没有存在的必要,因为如果为空的话,上面这行代码根本不可能执行到,所以findbug说这是冗余的空指针检查。当然考虑到特殊情况,这里显然是struts1的action,所以只要web应用正常启动,通常以下代码

?


1

createCorp
= (CreateCorpActionForm)form;

是不会导致createCorp指向空的,唯一的缺陷就是之前的new操作是多余的。

推荐修改:自己看着办

BUG-0003

Bug: con is null guaranteed to be dereferenced in com.bettersoft.admin.leftAction.getLeft(int, String, String) on exception path

There is a statement or branch on an exception path that if executed guarantees that a value is null at this point, and that value that is guaranteed to be dereferenced (except on forward paths involving runtime exceptions).

Confidence: Normal, Rank: (Troubling 11)

Pattern: NP_GUARANTEED_DEREF_ON_EXCEPTION_PATH

Type: NP, Category: CORRECTNESS (Correctness)

代码片段:

?


1

2

3

4

5

6

7

8

9

10

11

12

13

14

finally

        {

            try

            {

                if(rs
!=
null)

                    rs.close();

                if(ps!=null)

                    ps.close();

                con.close();

            }catch(Exception
ee)

            {

                ee.printStackTrace();

            }

        }

解释说明:这应该是大家很熟悉的代码片段了,可以想象Connection con是在catch代码块中进行的初始化操作,findbug对该bug说的很明白,说如果出现异常,Connection
con将保证为空,因为很显然如果出现异常,con将得不到正确的初始化,即便初始化了,因为异常的出现,引用也会被解除,回到一开始定义处的null状态,那么在这里的finally代码块中调用Connection con的close()方法,将报空指针异常

推荐修改:自己看着办

BUG-0004

Bug:
Possible null pointer dereference of dbVersion in com.bettersoft.admin.LoginAction.loadVersion(HttpServletRequest, ActionErrors) on exception path

A reference value which is null on some exception control path is dereferenced here. This may lead to aNullPointerExceptionwhen the code is executed. Note that because FindBugs currently does not prune infeasible exception paths, this may be a false warning.

Also note that FindBugs considers the default case of a switch statement to be an exception path, since the default case is often infeasible.

Confidence: Normal, Rank: Troubling (11)

Pattern: NP_NULL_ON_SOME_PATH_EXCEPTION

Type: NP, Category: CORRECTNESS (Correctness)

代码片段:

?


1

2

3

4

5

6

7

8

9

10

11

12

13

14

15

16

17

18

19

20

VersionInfo
dbVersion =
null;

    try

{

        con
= DBManager.getConnection();

        dbVersion
= vm.getVersionInfo(con);

    }
catch

(Exception e) {

        //
TODO Auto-generated catch block

        e.printStackTrace();

    }
finally

{

        try

{

            con.close();

        }
catch

(SQLException e) {

            //
TODO Auto-generated catch block

            e.printStackTrace();

        }

    }

if

(dbVersion.equals(programVersion)) {

    programVersion.setCorrent(true);

}
else

{

    programVersion.setCorrent(false);

}

解释说明:如果try catch 中捕获异常,那么dbVersion将为空,

?


1

dbVersion.equals(programVersion)

上面这行代码,将报空指针异常

BUG-0005

Bug: Dead store to am in com.bettersoft.approve.action.CheckAction.execute(ActionMapping, ActionForm, HttpServletRequest, HttpServletResponse)

This instruction assigns a value to a local variable, but the value is not read or used in any subsequent instruction. Often, this indicates an error, because the value computed is never used.

Note that Sun‘s javac compiler often generates dead stores for final local variables. Because FindBugs is a bytecode-based tool, there is no easy way to eliminate these false positives.

Confidence: High, Rank: Of Concern (15)

Pattern: DLS_DEAD_LOCAL_STORE

Type: DLS, Category: STYLE (Dodgy code)

代码片段:

?


1

ApproveManager
am =
new

ApproveManager();

解释说明:am这个局部变量创建出来后,没有在任何地方被引用。这里确实没有被引用,所以是个bug,但是findbug又说明了,这有可能是误报,因为javac编译器在编译局部常量时,也会产生dead stroes。所以这个要视情况而定,不能过于纠结

BUG-0006

Bug: The class name com.bettersoft.approve.form.BtWebCorp shadows the simple name of the superclass com.bettersoft.admin.BtWebCorp

This class has a simple name that is identical to that of its superclass, except that its superclass is in a different package (e.g.,alpha.Fooextendsbeta.Foo). This can be exceptionally confusing, create lots of situations in which you have to look at import
statements to resolve references and creates many opportunities to accidently define methods that do not override methods in their superclasses.

Confidence: High, Rank: Troubling (14)

Pattern: NM_SAME_SIMPLE_NAME_AS_SUPERCLASS

Type: Nm, Category: BAD_PRACTICE (Bad practice)

代码片段:

?


1

2

3

public

class

BtWebCorp
extends

com.bettersoft.admin.BtWebCorp{

}

解释说明:这里子类和父类名称一样,findbug认为这回导致很多混淆。显然一旦出问题,将很难发现,运行结果将出乎意料

BUG-0007

Bug: Comparison of String objects using == or != in com.byttersoft.admin.persistence.dao.MessageOpenDao.addOpenSave(MessageOpenForm)

This code comparesjava.lang.Stringobjects for reference equality using the == or != operators. Unless both strings are either constants in a source file, or have been interned using theString.intern()method, the same string value may be represented by two different
String objects. Consider using theequals(Object)method instead.

Confidence: Normal, Rank: Troubling (11)

Pattern: ES_COMPARING_STRINGS_WITH_EQ

Type: ES, Category: BAD_PRACTICE (Bad practice)

代码片段:

?


1

2

3

4

5

if(id==null

|| id==
""){

        sql
=
"insert
into xx values (1,?,?,?)"
;

}else{

        sql
=
"insert
into xx values ((select max(id) + 1 from xx),?,?,?)"
;

}

解释说明: 直接使用==进行对象实例比较,而没有使用equals,本来没觉得这个bug咋样,但是发现项目里居然最多的bug就是这个,不管是很多年前的代码还是最近的代码,都存在这大量这样的问题。看来这是一个通病,所以大家注意一下,不光是我们公司的项目有这样的问题,这应该是一个普遍的问题,尤其实在比较String类型的时候,注意只要不是java基本类型都需要使用equals进行比较,哪怕是自动解封的Integer,Double等

BUG-0008

Bug: Call to String.equals(Double) in com.byttersoft.amm.util.BalanceInterzoneRateUtil.formatRate(Double)

This method calls equals(Object) on two references of different class types with no common subclasses. Therefore, the objects being compared are unlikely to be members of the same class at runtime (unless some application classes were not analyzed, or dynamic
class loading can occur at runtime). According to the contract of equals(), objects of different classes should always compare as unequal; therefore, according to the contract defined by java.lang.Object.equals(Object), the result of this comparison will always
be false at runtime.

Confidence: High, Rank: Scariest (1)

Pattern: EC_UNRELATED_TYPES

Type: EC, Category: CORRECTNESS (Correctness)

代码片段:

?


1

2

3

4

5

private

static

String  formatRate(Double r){

        

        if(r==null

||  (
"undefined").equals(r)){

            return

null
;

        }

解释说明:使用equals比较不同类型的数据,"undefined"是String类型,r是Double类型,这两个比较肯定返回false

?


1

("undefined").equals(r)

上面这行代码完全没有必要 ,不可能存在这种情况

BUG-0009

Bug: Class com.byttersoft.util.CertInfo defines non-transient non-serializable instance field subjectDnAttr

This Serializable class defines a non-primitive instance field which is neither transient, Serializable, orjava.lang.Object, and does not appear to implement theExternalizableinterface or thereadObject()andwriteObject()methods. Objects of this class will not
be deserialized correctly if a non-Serializable object is stored in this field.

Confidence: High, Rank: Troubling (14)

Pattern: SE_BAD_FIELD

Type: Se, Category: BAD_PRACTICE (Bad practice)

代码片段:

?


1

2

3

4

5

6

7

8

9

10

11

12

13

14

15

16

public

class

CertInfo
implements

java.io.Serializable

{

    private

String subjectDN=
"";

    private

String issuerDN=
"";

    private

String notAfterDate=
"";

    private

String notBeforeDate=
"";

    private

String serialNumber=
"";

    private

String sigAlgName=
"";

    private

String sigAlgOID=
"";

    private

String version=
"";

    private

String publicKeyFormat=
"";

    private

String publicKeyAlgorithm=
"";

    private

Names subjectDnAttr=
null;

public

class

Names

{}<span></span>

解释说明: CertInfo实现的序列话,但是他的成员变量Names
subjectDnAttr没有实现序列化,这将会导致序列化失败,String已经默认实现了序列化。注意,序列化时所有的成员变量都必须递归的实现序列化,否则将导致序列化失败。如果某个成员变量不想被序列化要么标注为瞬态要么重写readObj方法

BUG-0010

Bug: Dead store to corpGourps rather than field with same name in com.byttersoft.admin.form.CorpGroupsForm.setCorpGourps(CorpGourps)

This instruction assigns a value to a local variable, but the value is not read or used in any subsequent instruction. Often, this indicates an error, because the value computed is never used. There is a field with the same name as the local variable. Did you
mean to assign to that variable instead?

Confidence: High, Rank: Scary (9)

Pattern: DLS_DEAD_LOCAL_STORE_SHADOWS_FIELD

Type: DLS, Category: STYLE (Dodgy code)

代码片段:

?


1

2

3

public

void

setCorpGourps(CorpGourps corpGourps) {

        corpGourps
= corpGourps;

    }

解释说明:成员变量和局部变量重名

BUG-0011

Bug: Invocation of toString on labelValue in com.byttersoft.approve.persistence.dao.MesAppDao.getMapByPara(String)

The code invokes toString on an array, which will generate a fairly useless result such as [[email protected] Consider using Arrays.toString to convert the array into a readable String that gives the contents of the array. See Programming Puzzlers, chapter 3, puzzle
12.

Confidence: Normal, Rank: Troubling (10)

Pattern: DMI_INVOKING_TOSTRING_ON_ARRAY

Type: USELESS_STRING, Category: CORRECTNESS (Correctness)

代码片段:

?


1

2

3

4

5

6

7

8

9

10

for

(String parameter : parameters) {

            String[]
labelValue = parameter.split(
"=");

            if

(labelValue.length ==
2)
{

                String
key = labelValue[
0];

                String
value = labelValue[
1];

                hashMap.put(key,
value);

            }
else

{

                logger.debug("参数
"

+ labelValue +
"
配置错误。"
);

            }

        }

解释说明:在进行日志输出时,直接输出对象,将默认调用对象的toString方法,而默认是输出对象的内存地址,所以这里显然有问题,本意应该是输出数组中的字符串

BUG-0012

Bug: Write to static field com.byttersoft.admin.service.BtSysResService.map from instance method com.byttersoft.admin.service.BtSysResService.hashCatchOfSysRes(boolean)

This instance method writes to a static field. This is tricky to get correct if multiple instances are being manipulated, and generally bad practice.

Confidence: High, Rank: Of Concern (15)

Pattern: ST_WRITE_TO_STATIC_FROM_INSTANCE_METHOD

Type: ST, Category: STYLE (Dodgy code)

代码片段:

?


1

2

3

4

5

6

7

8

9

10

11

static

Map<String, BtSysRes> map =
new

HashMap<String, BtSysRes>();

public

Map<String, BtSysRes> hashCatchOfSysRes(
boolean

isRefresh) {

        if(isRefresh
==
true){

            map
= hashCatchOfSysRes();

        }else{

            if(map
==
null

|| map.isEmpty()){

                map
= hashCatchOfSysRes();

            }

        }

        return

map;

    }

解释说明:在实例方法中修改类变量的引用,这会导致共享问题,因为其他实例也会访问该静态变量,但是却不知道某个实例已经修改了该静态变量的引用,导致不可预知的问题

推荐修改:将该方法改为类方法

BUG-0013

Bug: Unwritten field: com.byttersoft.admin.service.importservice.ImportServices.bank

This field is never written. All reads of it will return the default value. Check for errors (should it have been initialized?), or remove it if it is useless.

Confidence: Normal, Rank: Troubling (12)

Pattern: UWF_UNWRITTEN_FIELD

Type: UwF, Category: CORRECTNESS (Correctness)

代码片段:

?


1

2

3

4

5

6

public

class

ImportServices {

private

IBankAccServices bank;

public

IBankAccServices getBank() {

        return

bank;

    }

解释说明: bank对象为空,getBank方法返回了一个肯定为空的对象实例

BUG-0014

Bug: There is an apparent infinite recursive loop in com.byttersoft.amm.dao.impl.CheckLoanOrProvideInfoDaoImpl.addBatch(List)

This method unconditionally invokes itself. This would seem to indicate an infinite recursive loop that will result in a stack overflow.

Confidence: High, Rank: Scary (9)

Pattern: IL_INFINITE_RECURSIVE_LOOP

Type: IL, Category: CORRECTNESS (Correctness)

代码片段:

?


1

2

3

public

void

addBatch(List<CmsPLoanToBean> cmsPLoanBeans) {

        this.addBatch(cmsPLoanBeans);

    }

解释说明:出现了递归调用addBatch,将出现死循环

时间: 2024-08-05 11:17:03

Eclipse findbugs找出的bug案例说明的相关文章

找出诡异的Bug:数据怎么存不进去

带着学生做课程设计.程序一大,课程中做过了小项目,练过了分解动作,一到合起来了,难免还是要乱了分寸.事实上,实战的功夫,就是这样出来的.(课程设计指导视频链接(第36课时,3.18 银行系统开发).课程主页在链接,指导文档见链接,演示样例程序见链接). 话说,已经有两位做银行系统的同学和我说,"文件里写不进去数据. 程序一退出,明明写进去了.结果却是空文件."这不是一个小打击. 做软件,找Bug,有些像打空气,使半天劲.人家就不理你. 学计算机的人.练的就是这种功夫.要学会自己创建线索

如何写出没有BUG的代码?

1947年9月9日,美国海军准将 Grace Hopper 在哈佛学院计算机实验室里使用 Mark II 和 Mark III 计算机进行研究工作.她的团队跟踪到 Mark II 上的一个错误,操作人员发现是由于一只飞蛾钻到了 Mark II 的继电器里导致的.团队清除了这只飞蛾,一切恢复正常.当时的工作人员记录了这样一句日志:" First actual case of bug being found. "  这次著名的事件,犹如潘多拉打开了魔盒,从此,程序员的世界里,bug 满天飞

开发人员如何提高工作效率一:找出低效的原因

[高效能系列]开发人员如何提高工作效率一:找出低效的原因 高效能工作系列开篇,就以这一篇开发人员如何提高工作效率作为第一篇内容,写这个高效能工作系列的目的很明显,寻找各种可行的方法来提高自己的工作效率,包括时间管理的方法,如何实现目标等 1.  今天这篇的内容是找出效率低下的原因,有低效的开发人员,反过来就是高效的开发人员,那么这两者的效率差体现在哪里呢,把自己的情况也放进去比较                      十二个可让你效率提高的方面 比较方面 熟练人员 一般的开发人员 我 (20

[js]uploadify结合jqueryUI弹出框上传,js中的冒出的bug,又被ie坑了

引言 最近在一个项目中,在用户列表中需要对给没有签名样本的个别用户上传签名的样本,就想到博客园中上传图片使用弹出框方式,博客园具体怎么实现的不知道,只是如果自己来弄,想到两个插件的结合使用,在弹出框中使用uploadify插件进行上传,每次都会报错很是无语,最后找到解决方案,这里记录一下,算是对工作中遇到的bug的一个总结. bug 这是vs调试状态下,显示的信息.在浏览器端,点击第一次上传按钮,正常,将弹出框关闭后,第二次打开,就会出现问题: 第一次单击上传: 第二次,关闭弹出框,再次单击上传

水贴王之续,找出数组里出现频率最高的元素

找出数组里出现频率最高的元素 个人信息:就读于燕大本科软件工程专业 目前大三; 本人博客:google搜索"cqs_2012"即可; 个人爱好:酷爱数据结构和算法,希望将来从事算法工作为人民作出自己的贡献; 博客内容:水贴王问题之续 博客时间:2014-5-12; 编程语言:Java ; 编程坏境:Windows 7 专业版 x64; 编程工具:jdk,eclipse x64; 制图工具:office 2007 powerpoint; 硬件信息:7G-3 笔记本; 真言: 痛苦的活着比

一个N*M的矩阵,找出这个矩阵中所有元素的和不小于K的面积最小的子矩阵

题目描述: 一个N*M的矩阵,找出这个矩阵中所有元素的和不小于K的面积最小的子矩阵(矩阵中元素个数为矩阵面积) 输入: 每个案例第一行三个正整数N,M<=100,表示矩阵大小,和一个整数K 接下来N行,每行M个数,表示矩阵每个元素的值 输出: 输出最小面积的值.如果出现任意矩阵的和都小于K,直接输出-1. 样例输入: 4 4 10 1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 样例输出: 1 首先这个题应该是有一个动态规划的解法,不过好像复杂度也要到O(n^3lo

通过代码审计找出网站中的XSS漏洞实战(三)

一.背景 笔者此前录制了一套XSS的视频教程,在漏洞案例一节中讲解手工挖掘.工具挖掘.代码审计三部分内容,准备将内容用文章的形式再次写一此,前两篇已经写完,内容有一些关联性,其中手工XSS挖掘篇地址为快速找出网站中可能存在的XSS漏洞实践(一)https://segmentfault.com/a/1190000016095198 本文主要记录通过代码审计的方式进行XSS漏洞挖掘,分为了找出关键位置,正向审计,反向审计三个部分,审计的系统为permeate渗透测试系统,测试系统的搭建可以参考笔者的

Entity Framework 6 Recipes 2nd Edition(9-3)译-&gt;找出Web API中发生了什么变化

9-3. 找出Web API中发生了什么变化 问题 想通过基于REST的Web API服务对数据库进行插入,删除和修改对象图,而不必为每个实体类编写单独的更新方法. 此外, 用EF6的Code Frist实现数据访问管理. 本例,我们模拟一个N层场景,用单独的客户端(控制台应用)来调用单独的基于REST服务的Web网站(WEB API应用) . 注意:每层使用单独的Visual Studio 解决方案, 这样更方便配置.调试和模拟一个N层应用. 假设有一个如Figure 9-3所示的旅行社和预订

在一个SQL Server表中的多个列找出最大值

在一个SQL Server表中一行的多个列找出最大值 有时候我们需要从多个相同的列里(这些列的数据类型相同)找出最大的那个值,并显示 这里给出一个例子 IF (OBJECT_ID('tempdb..##TestTable') IS NOT NULL) DROP TABLE ##TestTable CREATE TABLE ##TestTable ( ID INT IDENTITY(1,1) PRIMARY KEY, Name NVARCHAR(40), UpdateByApp1Date DATE