Skip to content

Commit 9036ad6

Browse files
committed
Support the case where the array is defined by an assignment from
another array.
1 parent 581a6e7 commit 9036ad6

File tree

1 file changed

+47
-23
lines changed

1 file changed

+47
-23
lines changed

src/main/java/soot/dexpler/DexFillArrayDataTransformer.java

+47-23
Original file line numberDiff line numberDiff line change
@@ -91,30 +91,8 @@ protected void internalTransform(final Body body, String phaseName, Map<String,
9191
ArrayRef leftArray = (ArrayRef) left;
9292

9393
Local l = (Local) leftArray.getBase();
94-
List<Unit> assDefs = defs.getDefsOfAt(l, ass);
9594
List<Type> arrayTypes = new LinkedList<>();
96-
for (Unit d : assDefs) {
97-
if (d instanceof AssignStmt) {
98-
AssignStmt arrayAssign = (AssignStmt) d;
99-
Value source = arrayAssign.getRightOp();
100-
if (source instanceof NewArrayExpr) {
101-
NewArrayExpr newArray = (NewArrayExpr) source;
102-
arrayTypes.add(newArray.getBaseType());
103-
continue;
104-
}
105-
if (source instanceof InvokeExpr) {
106-
InvokeExpr invExpr = (InvokeExpr) source;
107-
Type aType = invExpr.getMethodRef().getReturnType();
108-
if (!(aType instanceof ArrayType)) {
109-
throw new InternalError("Failed to identify the array type. The identified method invocation "
110-
+ "does not return an array type. Invocation: " + invExpr.getMethodRef());
111-
}
112-
arrayTypes.add(((ArrayType) aType).getArrayElementType());
113-
continue;
114-
}
115-
throw new InternalError("Unsupported array definition statement: " + d);
116-
}
117-
}
95+
checkArrayDefinitions(l, ass, defs, arrayTypes);
11896
if (arrayTypes.isEmpty()) {
11997
throw new InternalError("Failed to determine the array type ");
12098
}
@@ -135,4 +113,50 @@ protected void internalTransform(final Body body, String phaseName, Map<String,
135113
}
136114
}
137115

116+
/**
117+
* Check the all available definitions of the current array to detect the array type and thus the type of the data loaded
118+
* by the array-fill-data instruction.
119+
*
120+
* @param l
121+
* local the array we are interested in is saved in
122+
* @param u
123+
* unit we start our search
124+
* @param defs
125+
* @param arrayTypes
126+
* result list containing the discovered array type(s)
127+
*/
128+
private void checkArrayDefinitions(Local l, Unit u, LocalDefs defs, List<Type> arrayTypes) {
129+
List<Unit> assDefs = defs.getDefsOfAt(l, u);
130+
for (Unit d : assDefs) {
131+
if (d instanceof AssignStmt) {
132+
AssignStmt arrayAssign = (AssignStmt) d;
133+
Value source = arrayAssign.getRightOp();
134+
if (source instanceof NewArrayExpr) {
135+
// array is assigned from a newly created array
136+
NewArrayExpr newArray = (NewArrayExpr) source;
137+
arrayTypes.add(newArray.getBaseType());
138+
continue;
139+
}
140+
if (source instanceof InvokeExpr) {
141+
// array is assigned from the return value of a function
142+
InvokeExpr invExpr = (InvokeExpr) source;
143+
Type aType = invExpr.getMethodRef().getReturnType();
144+
if (!(aType instanceof ArrayType)) {
145+
throw new InternalError("Failed to identify the array type. The identified method invocation "
146+
+ "does not return an array type. Invocation: " + invExpr.getMethodRef());
147+
}
148+
arrayTypes.add(((ArrayType) aType).getArrayElementType());
149+
continue;
150+
}
151+
if (source instanceof Local) {
152+
// our array is defined by an assignment from another array => check the definition of that other array.
153+
Local newLocal = (Local) source; // local of the "other array"
154+
checkArrayDefinitions(newLocal, d, defs, arrayTypes);
155+
continue;
156+
}
157+
throw new InternalError("Unsupported array definition statement: " + d);
158+
}
159+
}
160+
161+
}
138162
}

0 commit comments

Comments
 (0)