Soot中的SmartLocalDefs代码浅析

今天读了读Soot中的SmartLocalDefs类,因为在其mailing list里面至少有2封邮件[1][2]推荐看看这个类,慕名而来 :P 可惜的是,这个类相关的注释/文档太少,所以特此记录,以备后用。

首先这个类的成员包括5个域, 4个方法和1个内部类,下面就按次序简单描述一下各个部分。

[b]一. 域[/b]
1)
private final Map<Cons, ArrayList<Unit>> answer;

answer用于存储该类所做分析的最终结果:将(cons Unit Local)映射到其所有可能的def所在的Units

2)
private final Map<Local, HashSet<Unit>> localToDefs;

localToDefs将每个Local映射到定义它的所有Units

3)
private final UnitGraph graph;

graph是分析过程中所用的流图

4)
private final LocalDefsAnalysis analysis;

analysis是内部类LocalDefsAnalysis的一个引用,稍后具体介绍LocalDefsAnalysis

5)
private final Map<Unit, HashSet> unitToMask;

unitToMask将Unit映射到在该Unit之后依然live的Locals

[b]二. 方法[/b]
1)
public SmartLocalDefs(UnitGraph g, LiveLocals live)

类的构造函数,这个类的主要逻辑集中在该方法中(一大部分分析由内部类完成)。除了打印log之外,它干的活主要包括如下几个步骤:
[list]
[*]初始化graph, localToDefs,unitToMask
[*]将graph作为参数生成内部类LocalDefsAnalysis的一个实例。其实内部类在其构造函数被调用后,它已经默默的把主要的数据流分析都做完了 :o
[*]对于每个Unit(记为u),首先找出它use的Locals,然后将每一个Local(记为v)能到达该Unit的defs取出,最后构建一个(cons u v)并将其连同对应的defs放入answer.
[/list]

2)
private Local localDef(Unit u)

返回u当中定义的Local(即local变量)。[b]注意,方法里一个隐含的assertion是一个Unit至多能定义一个Local。[/b]

3)
private HashSet<Unit> defsOf( Local l )

返回l所有可能的defs。这个方法直接将l作为key从localToDefs里面去找value了,如果找不到就先put一个空的HashSet,然后将其返回。所以该方法的返回值总是non-null。

4)
public List<Unit> getDefsOfAt(Local l, Unit s)

这个方法就是client使用SmartLocalDefs的主要途径,即提供一个Local和一个Unit,获取在这个Unit中所有l的defs。

[b]三. 内部类[/b]
终于轮到苦工内部类LocalDefsAnalysis了。该类扩展了Soot框架提供的ForwardFlowAnalysis类,实现了一系列Soot进行数据流分析所需要的方法(关于这些方法的细节,可参考[3])。
这里就记录当前还没看太明白的问题:


protected void flowThrough(Object inValue, Object unit, Object outValue) {
Unit u = (Unit) unit;
HashSet in = (HashSet) inValue;
HashSet<Unit> out = (HashSet<Unit>) outValue;
out.clear();
Set mask = unitToMask.get(u);
Local l = localDef(u);
HashSet<Unit> allDefUnits = null;

if (l == null)
{//add all units contained in mask
for( Iterator inUIt = in.iterator(); inUIt.hasNext(); ) {
final Unit inU = (Unit) inUIt.next();
if( mask.contains(localDef(inU)) ){
out.add(inU);
}
}
}else
{//check unit whether contained in allDefUnits before add into out set.
allDefUnits = defsOf(l);

for( Iterator inUIt = in.iterator(); inUIt.hasNext(); ) {
final Unit inU = (Unit) inUIt.next();
if( mask.contains(localDef(inU)) )
{//only add unit not contained in allDefUnits
if ( allDefUnits.contains(inU)){
out.remove(inU);
} else {
out.add(inU);
}
}
}

out.removeAll(allDefUnits);
if(mask.contains(l)) out.add(u);
}
}

1)为什么倒数第2行还要removeAll?
2)为什么最后1行在out.add(u)之前还要判断l是否在mask中?

其实还有一个大问题:这个SmartLocalDefs和SimpleLocalDefs有什么具体区别?
等回头有时间了,再仔细琢磨琢磨吧 :wink:

[1] http://www.sable.mcgill.ca/pipermail/soot-list/2008-July/001872.html
[2] http://www.sable.mcgill.ca/pipermail/soot-list/2007-March/001084.html
[3] http://www.sable.mcgill.ca/soot/tutorial/analysis/index.html
  • 0
    点赞
  • 0
    收藏
    觉得还不错? 一键收藏
  • 0
    评论
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值