001: package net.sf.jdec.jvminstructions.commands;
002:
003: import java.util.ArrayList;
004: import java.util.List;
005: import java.util.Stack;
006:
007: import net.sf.jdec.core.DecompilerHelper;
008: import net.sf.jdec.core.GlobalVariableStore;
009: import net.sf.jdec.core.JvmOpCodes;
010: import net.sf.jdec.core.Operand;
011: import net.sf.jdec.core.OperandStack;
012: import net.sf.jdec.reflection.Behaviour;
013: import net.sf.jdec.util.Util;
014:
015: public class SastoreCommand extends AbstractInstructionCommand {
016:
017: public SastoreCommand(Behaviour context) {
018: super (context);
019:
020: }
021:
022: public int getSkipBytes() {
023: return 0;
024: }
025:
026: public void execute() {
027: byte[] info = getCode();
028: Operand op = null;
029: Operand op1 = null;
030: Operand op2 = null;
031: List skipaastores = GlobalVariableStore.getSkipaastores();
032: boolean specialIASTORE = GlobalVariableStore.isSpecialIASTORE();
033: boolean primitiveastore = GlobalVariableStore
034: .isPrimitiveastore();
035: int arraytimespush = GlobalVariableStore.getArraytimespush();
036: StringBuffer addtype = new StringBuffer();
037: OperandStack opStack = getStack();
038: Behaviour behavior = getContext();
039: int currentForIndex = getCurrentInstPosInCode();
040: ArrayList skipPrimitiveArrayStores = GlobalVariableStore
041: .getSkipPrimitiveArrayStores();
042: Stack arraytimesstack = GlobalVariableStore
043: .getArraytimesstack();
044: boolean b = DecompilerHelper.checkForArrayPostIncrement(
045: currentForIndex, opStack, info, "category1", addtype);
046: boolean bl2 = DecompilerHelper
047: .checkForArrayMultiAssignablePostIncrement(
048: currentForIndex, opStack, getCode(),
049: "category1");
050: if (b && opStack.size() > 0 && arraytimesstack.size() == 0) {
051: op = (Operand) opStack.pop();
052: op1 = (Operand) opStack.pop();
053: op2 = (Operand) opStack.pop();
054:
055: java.lang.String temp = "";
056: if (addtype.toString().equals("add"))
057: temp += op2.getOperandValue() + "["
058: + op1.getOperandValue() + "]" + "++";
059: else
060: temp += op2.getOperandValue() + "["
061: + op1.getOperandValue() + "]" + "--";
062: Operand o = opStack.peekTopOfStack();
063: o.setOperandValue(temp);
064:
065: } else if (bl2 && opStack.size() > 0
066: && arraytimesstack.size() == 0) {
067: op = (Operand) opStack.pop();
068: op1 = (Operand) opStack.pop();
069: op2 = (Operand) opStack.pop();
070:
071: java.lang.String temp = "";
072: temp += op2.getOperandValue() + "[" + op1.getOperandValue()
073: + "]" + "=";
074: Operand o = opStack.peekTopOfStack();
075: temp = temp + o.getOperandValue();
076: o.setOperandValue(temp);
077: }
078:
079: else {
080: if (skipPrimitiveArrayStores.contains(new Integer(
081: currentForIndex)) == false) {
082: java.lang.String tempString = "";
083: op = (Operand) opStack.pop();
084: op1 = (Operand) opStack.pop();
085: if (opStack.size() > 0) {
086: op2 = (Operand) opStack.pop();
087: tempString = op2.getOperandValue() + "["
088: + op1.getOperandValue() + "]="
089: + op.getOperandValue() + ";\n";
090: }
091: if (arraytimesstack.size() == 0) {
092: int curpos = currentForIndex;
093: if (curpos - 3 > 0
094: && (info[curpos - 1] == JvmOpCodes.DUP_X2
095: || info[curpos - 1] == JvmOpCodes.DUP
096: || info[curpos - 1] == JvmOpCodes.DUP2
097: || info[curpos - 1] == JvmOpCodes.DUP_X1
098: || info[curpos - 1] == JvmOpCodes.DUP2_X1 || info[curpos - 1] == JvmOpCodes.DUP2_X2)
099: && info[curpos - 2] == JvmOpCodes.I2S
100: && info[curpos - 3] == JvmOpCodes.IADD) {
101: tempString = "++" + op2.getOperandValue() + "["
102: + op1.getOperandValue() + "]";
103: java.lang.String v1 = op2.getOperandValue()
104: + "[" + op1.getOperandValue() + "]";
105: java.lang.String v2 = opStack.peekTopOfStack()
106: .getOperandValue();
107: if (v2.equals(v1)) {
108: opStack.pop();
109: }
110:
111: opStack.push(createOperand(tempString));
112: } else if (curpos - 3 > 0
113: && (info[curpos - 1] == JvmOpCodes.DUP_X2
114: || info[curpos - 1] == JvmOpCodes.DUP
115: || info[curpos - 1] == JvmOpCodes.DUP2
116: || info[curpos - 1] == JvmOpCodes.DUP_X1
117: || info[curpos - 1] == JvmOpCodes.DUP2_X1 || info[curpos - 1] == JvmOpCodes.DUP2_X2)
118: && info[curpos - 2] == JvmOpCodes.I2S
119: && info[curpos - 3] == JvmOpCodes.ISUB) {
120: tempString = "--" + op2.getOperandValue() + "["
121: + op1.getOperandValue() + "]";
122: java.lang.String v1 = op2.getOperandValue()
123: + "[" + op1.getOperandValue() + "]";
124: java.lang.String v2 = opStack.peekTopOfStack()
125: .getOperandValue();
126: if (v2.equals(v1)) {
127: opStack.pop();
128: }
129: opStack.push(createOperand(tempString));
130: } else if (curpos - 4 > 0
131: && info[curpos - 1] == JvmOpCodes.I2S
132: && info[curpos - 2] == JvmOpCodes.IADD
133: && info[curpos - 3] == JvmOpCodes.ICONST_1
134: && (info[curpos - 4] == JvmOpCodes.DUP_X2
135: || info[curpos - 4] == JvmOpCodes.DUP
136: || info[curpos - 4] == JvmOpCodes.DUP2
137: || info[curpos - 4] == JvmOpCodes.DUP_X1
138: || info[curpos - 4] == JvmOpCodes.DUP2_X1 || info[curpos - 4] == JvmOpCodes.DUP2_X2)) {
139: tempString = op2.getOperandValue() + "["
140: + op1.getOperandValue() + "]++";
141: java.lang.String v1 = op2.getOperandValue()
142: + "[" + op1.getOperandValue() + "]";
143: java.lang.String v2 = opStack.peekTopOfStack()
144: .getOperandValue();
145: if (v2.equals(v1)) {
146: opStack.pop();
147: }
148: opStack.push(createOperand(tempString));
149: } else if (curpos - 4 > 0
150: && info[curpos - 1] == JvmOpCodes.I2S
151: && info[curpos - 2] == JvmOpCodes.ISUB
152: && info[curpos - 3] == JvmOpCodes.ICONST_1
153: && (info[curpos - 4] == JvmOpCodes.DUP_X2
154: || info[curpos - 4] == JvmOpCodes.DUP
155: || info[curpos - 4] == JvmOpCodes.DUP2
156: || info[curpos - 4] == JvmOpCodes.DUP_X1
157: || info[curpos - 4] == JvmOpCodes.DUP2_X1 || info[curpos - 4] == JvmOpCodes.DUP2_X2)) {
158: tempString = op2.getOperandValue() + "["
159: + op1.getOperandValue() + "]--";
160: java.lang.String v1 = op2.getOperandValue()
161: + "[" + op1.getOperandValue() + "]";
162: java.lang.String v2 = opStack.peekTopOfStack()
163: .getOperandValue();
164: if (v2.equals(v1)) {
165: opStack.pop();
166: }
167: opStack.push(createOperand(tempString));
168: } else {
169: if (skipPrimitiveArrayStores
170: .contains(new Integer(currentForIndex)) == false) {
171: behavior
172: .appendToBuffer(Util
173: .formatDecompiledStatement(tempString));
174: }
175: }
176: } else {
177:
178: primitiveastore = true;
179: java.lang.String newvalue = "";
180: arraytimespush = Integer.parseInt(arraytimesstack
181: .peek().toString());
182: if (arraytimespush > 0) {
183:
184: int curpos = currentForIndex;
185:
186: if (curpos - 3 > 0
187: && DecompilerHelper
188: .isArrayElement(curpos + 1)
189: && (info[curpos - 1] == JvmOpCodes.DUP_X2
190: || info[curpos - 1] == JvmOpCodes.DUP
191: || info[curpos - 1] == JvmOpCodes.DUP2
192: || info[curpos - 1] == JvmOpCodes.DUP_X1
193: || info[curpos - 1] == JvmOpCodes.DUP2_X1 || info[curpos - 1] == JvmOpCodes.DUP2_X2)
194: && info[curpos - 2] == JvmOpCodes.I2S
195: && info[curpos - 3] == JvmOpCodes.IADD) {
196: if (!newfound())
197: newvalue = "++" + op2.getOperandValue()
198: + "[" + op1.getOperandValue()
199: + "]";
200: else {
201: if (opStack.size() > 0) {
202: java.lang.String topv = opStack
203: .getTopOfStack()
204: .getOperandValue();
205: if (topv.trim().startsWith("++")) {
206: newvalue = op2
207: .getOperandValue()
208: + topv;
209: } else
210: newvalue = "++"
211: + op2.getOperandValue()
212: + topv;
213: if (topv.equals(opStack
214: .peekTopOfStack()
215: .getOperandValue())) {
216: opStack.pop();
217: }
218: }
219: }
220:
221: } else if (curpos - 3 > 0
222: && DecompilerHelper
223: .isArrayElement(curpos + 1)
224: && (info[curpos - 1] == JvmOpCodes.DUP_X2
225: || info[curpos - 1] == JvmOpCodes.DUP
226: || info[curpos - 1] == JvmOpCodes.DUP2
227: || info[curpos - 1] == JvmOpCodes.DUP_X1
228: || info[curpos - 1] == JvmOpCodes.DUP2_X1 || info[curpos - 1] == JvmOpCodes.DUP2_X2)
229: && info[curpos - 2] == JvmOpCodes.I2S
230: && info[curpos - 3] == JvmOpCodes.ISUB) {
231: if (!newfound())
232: newvalue = "--" + op2.getOperandValue()
233: + "[" + op1.getOperandValue()
234: + "]";
235: else {
236: if (opStack.size() > 0) {
237:
238: java.lang.String topv = opStack
239: .getTopOfStack()
240: .getOperandValue();
241: if (topv.trim().startsWith("--")) {
242: newvalue = op2
243: .getOperandValue()
244: + topv;
245: } else
246: newvalue = "--"
247: + op2.getOperandValue()
248: + topv;//
249: if (topv.equals(opStack
250: .peekTopOfStack()
251: .getOperandValue())) {
252: opStack.pop();
253: }
254:
255: }
256: }
257:
258: } else if (curpos - 4 > 0
259: && DecompilerHelper
260: .isArrayElement(curpos + 1)
261: && info[curpos - 1] == JvmOpCodes.I2S
262: && info[curpos - 2] == JvmOpCodes.IADD
263: && (info[curpos - 3] == JvmOpCodes.ICONST_1
264: || info[curpos - 4] == JvmOpCodes.DUP_X2
265: || info[curpos - 4] == JvmOpCodes.DUP
266: || info[curpos - 4] == JvmOpCodes.DUP2
267: || info[curpos - 4] == JvmOpCodes.DUP_X1
268: || info[curpos - 4] == JvmOpCodes.DUP2_X1 || info[curpos - 4] == JvmOpCodes.DUP2_X2)) {
269: if (!newfound())
270: newvalue = op2.getOperandValue() + "["
271: + op1.getOperandValue() + "]++";
272: else {
273: if (opStack.size() > 0) {
274:
275: java.lang.String topv = opStack
276: .getTopOfStack()
277: .getOperandValue();
278: newvalue = op2.getOperandValue()
279: + topv + "++";
280: if (topv.equals(opStack
281: .peekTopOfStack()
282: .getOperandValue())) {
283: opStack.pop();
284: }
285:
286: }
287: }
288:
289: } else if (curpos - 4 > 0
290: && DecompilerHelper
291: .isArrayElement(curpos + 1)
292: && info[curpos - 1] == JvmOpCodes.I2S
293: && info[curpos - 2] == JvmOpCodes.ISUB
294: && (info[curpos - 3] == JvmOpCodes.ICONST_1
295: || info[curpos - 4] == JvmOpCodes.DUP_X2
296: || info[curpos - 4] == JvmOpCodes.DUP
297: || info[curpos - 4] == JvmOpCodes.DUP2
298: || info[curpos - 4] == JvmOpCodes.DUP_X1
299: || info[curpos - 4] == JvmOpCodes.DUP2_X1 || info[curpos - 4] == JvmOpCodes.DUP2_X2)) {
300:
301: if (!newfound())
302: newvalue = op2.getOperandValue() + "["
303: + op1.getOperandValue() + "]--";
304: else {
305: if (opStack.size() > 0) {
306:
307: java.lang.String topv = opStack
308: .getTopOfStack()
309: .getOperandValue();
310: newvalue = op2.getOperandValue()
311: + topv + "--";
312: if (topv.equals(opStack
313: .peekTopOfStack()
314: .getOperandValue())) {
315: opStack.pop();
316: }
317: }
318: }
319:
320: } else
321: newvalue = "";
322: if (newvalue.length() > 0) {
323: StringBuffer v = new StringBuffer("");
324: int c = getGenericFinder()
325: .isNextInstructionConversionInst(
326: currentForIndex + 1, v);
327: if (c != -1
328: && newvalue.indexOf(v.toString()) == -1) {
329: newvalue = "(" + v.toString() + ")"
330: + newvalue;
331: }
332: }
333:
334: /////////////////
335: if (skipPrimitiveArrayStores
336: .contains(new Integer(currentForIndex)) == false) {
337:
338: if (newfound()) {
339: //z=createOperand(op.getOperandValue());
340: //Operand y=opStack.getTopOfStack();
341: java.lang.String newv = op2
342: .getOperandValue()
343: + op.getOperandValue();
344: if (newvalue.length() > 0) {
345: newv = newvalue;
346: specialIASTORE = true;
347: }
348: arraytimespush = Integer
349: .parseInt(arraytimesstack.pop()
350: .toString());
351: arraytimespush--;
352: if (arraytimespush == 0) {
353: newv += "}";
354: } else {
355: arraytimesstack.push(""
356: + arraytimespush);
357: newv += ",";
358: }
359: opStack.push(createOperand(newv));
360: } else {
361: arraytimespush = Integer
362: .parseInt(arraytimesstack.pop()
363: .toString());
364: arraytimespush--;
365: if (arraytimespush == 0) {
366: boolean closeImmediate = false; // for the parent actually
367: if (arraytimesstack.size() > 0) {
368: int oldstacksize = Integer
369: .parseInt(arraytimesstack
370: .pop()
371: .toString());
372: int newstacksize = oldstacksize - 1;
373: if (newstacksize != 0)
374: arraytimesstack.push(""
375: + newstacksize);
376: else
377: closeImmediate = true;
378: //behavior.appendToBuffer("}";
379: }
380:
381: if (arraytimesstack.isEmpty()) {
382: if (newvalue.length() > 0) {
383: behavior
384: .appendToBuffer(newvalue
385: + "}");
386: int count = arrayClosingBracketCount(currentForIndex);
387: java.lang.String temp = "";
388: for (int z = 1; z <= count; z++) {
389: temp += "\n}";
390: if (z < count)
391: temp += "\n";
392:
393: }
394: //Util.forceNewLine=false;
395: Util.forceTrimLines = false;
396: behavior
397: .appendToBuffer(Util
398: .formatDecompiledStatement(temp)
399: + ";\n");
400: Util.forceNewLine = true;
401: Util.forceTrimLines = true;
402: specialIASTORE = true;
403: } else {
404: behavior.appendToBuffer(op
405: .getOperandValue()
406: + "}");
407: int count = arrayClosingBracketCount(currentForIndex);
408: java.lang.String temp = "";
409: for (int z = 1; z <= count; z++) {
410: temp += "\n}";
411: if (z < count)
412: temp += "\n";
413: }
414: Util.forceStartSpace = false;
415: Util.forceNewLine = false;
416: Util.forceTrimLines = false;
417: behavior
418: .appendToBuffer(Util
419: .formatDecompiledStatement(temp)
420: + ";\n");
421: Util.forceStartSpace = true;
422: Util.forceTrimLines = false;
423: Util.forceNewLine = true;
424: }
425: } else {
426: if (newvalue.length() > 0) {
427: behavior
428: .appendToBuffer(newvalue
429: + "},");
430: specialIASTORE = true;
431: } else {
432: behavior.appendToBuffer(op
433: .getOperandValue()
434: + "},");
435: }
436: if (closeImmediate) {
437: do {
438: Util.forceStartSpace = false;
439: Util.forceNewLine = false;
440: Util.forceTrimLines = false;
441: if (arraytimesstack
442: .size() > 0)
443: behavior
444: .appendToBuffer(Util
445: .formatDecompiledStatement("\n},\n"));
446: else {
447: behavior
448: .appendToBuffer(Util
449: .formatDecompiledStatement("\n};\n"));
450: }
451: Util.forceStartSpace = true;
452: Util.forceNewLine = true;
453: Util.forceTrimLines = true;
454:
455: if (arraytimesstack
456: .size() > 0) {
457: int oldstacksize = Integer
458: .parseInt(arraytimesstack
459: .pop()
460: .toString());
461: int newstacksize = oldstacksize - 1;
462: if (newstacksize != 0) {
463: arraytimesstack
464: .push(""
465: + newstacksize);
466: closeImmediate = false;
467: } else {
468: closeImmediate = true;
469: }
470: } else {
471: closeImmediate = false;
472: }
473:
474: } while (closeImmediate);
475:
476: }
477:
478: }
479:
480: } else {
481: arraytimesstack.push(""
482: + arraytimespush);
483: /*if(isThisInstrStart(starts,(currentForIndex-1)) && isInstructionAnyDUP(info[currentForIndex-1]) && newvalue!=null && newvalue.trim().length() > 0){
484: if(newvalue!=null && (newvalue.trim().startsWith("++") || newvalue.trim().startsWith("--")) && opStack.size() > 0) {
485: java.lang.String tpv=opStack.peekTopOfStack().getOperandValue().trim();
486: if("++".concat(tpv).equals(newvalue) || "--".concat(tpv).equals(newvalue)){
487: opStack.pop();
488: }
489: }
490:
491: opStack.push(createOperand(newvalue));
492: }*/
493: // else{
494: if (newvalue.length() > 0) {
495: behavior
496: .appendToBuffer(newvalue
497: + ",");
498: specialIASTORE = true;
499: } else {
500: if (getStoreFinder()
501: .isInstPrimitiveArrayStore(
502: info[(currentForIndex + 1)])
503: && tempString != null
504: && tempString.length() > 0)
505: behavior
506: .appendToBuffer(tempString);
507: else
508: behavior.appendToBuffer(op
509: .getOperandValue()
510: + ",");
511: }
512: // }
513: }
514: }
515: }
516: }
517: }
518: } else {
519:
520: if (opStack.size() > 2 && !newfound()) {
521: opStack.pop();
522: opStack.pop();
523: }
524:
525: }
526: int nextinst = info[currentForIndex + 1];
527: if (getGenericFinder()
528: .isThisInstrStart(currentForIndex + 1)
529: && nextinst == JvmOpCodes.AASTORE) {
530: skipaastores.add(new Integer(currentForIndex + 1));
531: }
532:
533: }
534:
535: GlobalVariableStore.setSpecialIASTORE(specialIASTORE);
536: GlobalVariableStore.setArraytimespush(arraytimespush);
537: GlobalVariableStore.setPrimitiveastore(primitiveastore);
538:
539: }
540:
541: }
|