Merge origin/master

This commit is contained in:
Jindra Petřík
2014-11-22 06:23:09 +01:00
33 changed files with 1028 additions and 1000 deletions

View File

@@ -163,23 +163,24 @@ public class IdentifiersDeobfuscation {
} else {
parts = new String[]{pkg};
}
String ret = "";
StringBuilder ret = new StringBuilder();
boolean isChanged = false;
for (int p = 0; p < parts.length; p++) {
if (p > 0) {
ret += ".";
ret.append(".");
}
String partChanged = deobfuscateName(as3, parts[p], false, "package", namesMap, renameType, selected);
if (partChanged != null) {
ret += partChanged;
ret.append(partChanged);
isChanged = true;
} else {
ret += parts[p];
ret.append(parts[p]);
}
}
if (isChanged) {
namesMap.put(pkg, ret);
return ret;
String retStr = ret.toString();
namesMap.put(pkg, retStr);
return retStr;
}
return null;
}
@@ -328,15 +329,16 @@ public class IdentifiersDeobfuscation {
} else {
parts = new String[]{pkg};
}
String ret = "";
StringBuilder ret = new StringBuilder();
for (int i = 0; i < parts.length; i++) {
if (i > 0) {
ret += ".";
ret.append(".");
}
ret += printIdentifier(as3, parts[i], validNameExceptions);
ret.append(printIdentifier(as3, parts[i], validNameExceptions));
}
nameCache.put(pkg, ret);
return ret;
String retStr = ret.toString();
nameCache.put(pkg, retStr);
return retStr;
}
public static String escapeOIdentifier(String s) {

View File

@@ -79,8 +79,14 @@ import com.jpexs.decompiler.flash.exporters.settings.ShapeExportSettings;
import com.jpexs.decompiler.flash.exporters.settings.SoundExportSettings;
import com.jpexs.decompiler.flash.exporters.settings.TextExportSettings;
import com.jpexs.decompiler.flash.exporters.shape.CanvasShapeExporter;
import com.jpexs.decompiler.flash.abc.CachedDecompilation;
import com.jpexs.decompiler.flash.abc.types.ScriptInfo;
import com.jpexs.decompiler.flash.action.CachedScript;
import com.jpexs.decompiler.flash.helpers.HighlightedText;
import com.jpexs.decompiler.flash.helpers.HighlightedTextWriter;
import com.jpexs.decompiler.flash.helpers.SWFDecompilerPlugin;
import com.jpexs.decompiler.flash.helpers.collections.MyEntry;
import com.jpexs.decompiler.flash.helpers.hilight.Highlighting;
import com.jpexs.decompiler.flash.tags.ABCContainerTag;
import com.jpexs.decompiler.flash.tags.DefineBinaryDataTag;
import com.jpexs.decompiler.flash.tags.DefineSpriteTag;
@@ -271,6 +277,10 @@ public final class SWF implements SWFContainerItem, Timelined {
public DumpInfoSwfNode dumpInfo;
public DefineBinaryDataTag binaryData;
private static Cache<String, SerializableImage> frameCache = Cache.getInstance(false);
private final Cache<ASMSource, CachedScript> as2Cache = Cache.getInstance(true);
private final Cache<ScriptPack, CachedDecompilation> as3Cache = Cache.getInstance(true);
public void updateCharacters() {
characters.clear();
parseCharacters(new ArrayList<ContainerItem>(tags));
@@ -312,6 +322,10 @@ public final class SWF implements SWFContainerItem, Timelined {
for (Integer id : needed) {
if (!addedCharacterIds.contains(id)) {
CharacterTag neededCharacter = characters.get(id);
if (neededCharacter == null) {
continue;
}
if (movedTags.contains(neededCharacter)) {
logger.log(Level.SEVERE, "Fixing characters order failed, recursion detected.");
return;
@@ -633,6 +647,13 @@ public final class SWF implements SWFContainerItem, Timelined {
throw new IOException("Invalid SWF file. No known tag found.");
}
}
/* preload shape tags
for (Tag tag : tags) {
if (tag instanceof ShapeTag) {
((ShapeTag) tag).getShapes();
}
}*/
}
@Override
@@ -2061,10 +2082,12 @@ public final class SWF implements SWFContainerItem, Timelined {
public void exportFla(AbortRetryIgnoreHandler handler, String outfile, String swfName, String generator, String generatorVerName, String generatorVersion, boolean parallel, FLAVersion version) throws IOException {
XFLConverter.convertSWF(handler, this, swfName, outfile, true, generator, generatorVerName, generatorVersion, parallel, version);
clearAllCache();
}
public void exportXfl(AbortRetryIgnoreHandler handler, String outfile, String swfName, String generator, String generatorVerName, String generatorVersion, boolean parallel, FLAVersion version) throws IOException {
XFLConverter.convertSWF(handler, this, swfName, outfile, false, generator, generatorVerName, generatorVersion, parallel, version);
clearAllCache();
}
public static AffineTransform matrixToTransform(MATRIX mat) {
@@ -2073,8 +2096,6 @@ public final class SWF implements SWFContainerItem, Timelined {
mat.translateX, mat.translateY);
}
private static Cache<String, SerializableImage> frameCache = Cache.getInstance(false);
public static SerializableImage getFromCache(String key) {
if (frameCache.contains(key)) {
return SWF.frameCache.get(key);
@@ -2088,8 +2109,80 @@ public final class SWF implements SWFContainerItem, Timelined {
}
}
public static void clearImageCache() {
public void clearImageCache() {
frameCache.clear();
for (Tag tag : tags) {
if (tag instanceof ImageTag) {
((ImageTag) tag).clearCache();
}
}
}
public void clearScriptCache() {
as2Cache.clear();
as3Cache.clear();
}
public void clearAllCache() {
clearImageCache();
clearScriptCache();
Cache.clearAll();
System.gc();
}
public static void uncache(ASMSource src) {
src.getSwf().as2Cache.remove(src);
}
public static void uncache(ScriptPack pack) {
pack.getSwf().as3Cache.remove(pack);
}
public static boolean isCached(ASMSource src) {
return src.getSwf().as2Cache.contains(src);
}
public static boolean isCached(ScriptPack pack) {
return pack.getSwf().as3Cache.contains(pack);
}
public static CachedScript getCached(ASMSource src, ActionList actions) throws InterruptedException {
SWF swf = src.getSwf();
if (swf.as2Cache.contains(src)) {
return swf.as2Cache.get(src);
}
if (actions == null) {
actions = src.getActions();
}
HighlightedTextWriter writer = new HighlightedTextWriter(Configuration.getCodeFormatting(), true);
Action.actionsToSource(src, actions, src.toString()/*FIXME?*/, writer);
List<Highlighting> hilights = writer.instructionHilights;
String srcNoHex = writer.toString();
CachedScript res = new CachedScript(srcNoHex, hilights);
swf.as2Cache.put(src, res);
return res;
}
public static CachedDecompilation getCached(ScriptPack pack) throws InterruptedException {
SWF swf = pack.getSwf();
if (swf.as3Cache.contains(pack)) {
return swf.as3Cache.get(pack);
}
int scriptIndex = pack.scriptIndex;
ScriptInfo script = null;
if (scriptIndex > -1) {
script = pack.abc.script_info.get(scriptIndex);
}
boolean parallel = Configuration.parallelSpeedUp.get();
HighlightedTextWriter writer = new HighlightedTextWriter(Configuration.getCodeFormatting(), true);
pack.toSource(writer, swf.abcList, script.traits.traits, ScriptExportMode.AS, parallel);
HighlightedText hilightedCode = new HighlightedText(writer);
CachedDecompilation res = new CachedDecompilation(hilightedCode);
swf.as3Cache.put(pack, res);
return res;
}
public static RECT fixRect(RECT rect) {

View File

@@ -14,7 +14,7 @@
* You should have received a copy of the GNU General Public License
* along with this program. If not, see <http://www.gnu.org/licenses/>.
*/
package com.jpexs.decompiler.flash.gui.abc;
package com.jpexs.decompiler.flash.abc;
import com.jpexs.decompiler.flash.helpers.HighlightedText;
import com.jpexs.decompiler.flash.helpers.hilight.Highlighting;

View File

@@ -174,18 +174,18 @@ public class AVM2Deobfuscation {
} else {
parts = new String[]{s};
}
String ret = "";
StringBuilder ret = new StringBuilder();
for (int p = 0; p < parts.length; p++) {
if (p > 0) {
ret += ".";
ret.append(".");
}
if (!isValidNSPart(parts[p])) {
ret += fooString(namesMap, parts[p], false, DEFAULT_FOO_SIZE, "package", renameType);
ret.append(fooString(namesMap, parts[p], false, DEFAULT_FOO_SIZE, "package", renameType));
} else {
ret += parts[p];
ret.append(parts[p]);
}
}
newName = ret;
newName = ret.toString();
namesMap.put(s, newName);
}
if (stringUsages.contains(strIndex)) {

View File

@@ -269,16 +269,16 @@ public class Multiname {
}
public String getNameWithNamespace(AVM2ConstantPool constants, boolean raw) {
String ret = "";
StringBuilder ret = new StringBuilder();
Namespace ns = getNamespace(constants);
if (ns != null) {
String nsname = ns.getName(constants, raw);
if (nsname != null && !nsname.isEmpty()) {
ret += nsname + ".";
ret.append(nsname).append(".");
}
}
ret += getName(constants, null, raw);
return ret;
ret.append(getName(constants, null, raw));
return ret.toString();
}
public Namespace getNamespace(AVM2ConstantPool constants) {

View File

@@ -755,9 +755,7 @@ public class Action implements GraphSourceItem {
* @throws java.lang.InterruptedException
*/
public static List<GraphTargetItem> actionsToTree(HashMap<Integer, String> regNames, HashMap<String, GraphTargetItem> variables, HashMap<String, GraphTargetItem> functions, List<Action> actions, int version, int staticOperation, String path) throws InterruptedException {
//Stack<ActionItem> stack = new Stack<ActionItem>();
return ActionGraph.translateViaGraph(regNames, variables, functions, actions, version, staticOperation, path);
//return actionsToTree(regNames, stack, actions, 0, actions.size() - 1, version);
}
@Override

View File

@@ -1,36 +1,36 @@
/*
* Copyright (C) 2010-2014 JPEXS
*
* This program is free software: you can redistribute it and/or modify
* it under the terms of the GNU General Public License as published by
* the Free Software Foundation, either version 3 of the License, or
* (at your option) any later version.
*
* This program is distributed in the hope that it will be useful,
* but WITHOUT ANY WARRANTY; without even the implied warranty of
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
* GNU General Public License for more details.
*
* You should have received a copy of the GNU General Public License
* along with this program. If not, see <http://www.gnu.org/licenses/>.
*/
package com.jpexs.decompiler.flash.gui.action;
import com.jpexs.decompiler.flash.helpers.hilight.Highlighting;
import java.io.Serializable;
import java.util.List;
/**
*
* @author JPEXS
*/
public class CachedScript implements Serializable {
public String text;
List<Highlighting> hilights;
public CachedScript(String text, List<Highlighting> hilights) {
this.text = text;
this.hilights = hilights;
}
}
/*
* Copyright (C) 2010-2014 JPEXS
*
* This program is free software: you can redistribute it and/or modify
* it under the terms of the GNU General Public License as published by
* the Free Software Foundation, either version 3 of the License, or
* (at your option) any later version.
*
* This program is distributed in the hope that it will be useful,
* but WITHOUT ANY WARRANTY; without even the implied warranty of
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
* GNU General Public License for more details.
*
* You should have received a copy of the GNU General Public License
* along with this program. If not, see <http://www.gnu.org/licenses/>.
*/
package com.jpexs.decompiler.flash.action;
import com.jpexs.decompiler.flash.helpers.hilight.Highlighting;
import java.io.Serializable;
import java.util.List;
/**
*
* @author JPEXS
*/
public class CachedScript implements Serializable {
public String text;
public List<Highlighting> hilights;
public CachedScript(String text, List<Highlighting> hilights) {
this.text = text;
this.hilights = hilights;
}
}

View File

@@ -82,20 +82,20 @@ public class CanvasMorphShapeExporter extends MorphShapeExporterBase {
}
public static String getJsSuffix(int width, int height) {
String ret = "";
ret += "}\r\n";
StringBuilder ret = new StringBuilder();
ret.append("}\r\n");
int step = Math.round(65535 / 100);
int rate = 10;
ret += "var step = " + step + ";\r\n";
ret += "var ratio = -1;\r\n";
ret += "function nextFrame(ctx){\r\n";
ret += "\tctx.clearRect(0,0," + width + "," + height + ");\r\n";
ret += "\tratio = (ratio+step)%65535;\r\n";
ret += "\tmorphshape(ctx,ratio);\r\n";
ret += "}\r\n";
ret += "window.setInterval(function(){nextFrame(ctx)}," + rate + ");\r\n";
ret += CanvasShapeExporter.getJsSuffix();
return ret;
ret.append("var step = ").append(step).append(";\r\n");
ret.append("var ratio = -1;\r\n");
ret.append("function nextFrame(ctx){\r\n");
ret.append("\tctx.clearRect(0,0,").append(width).append(",").append(height).append(");\r\n");
ret.append("\tratio = (ratio+step)%65535;\r\n");
ret.append("\tmorphshape(ctx,ratio);\r\n");
ret.append("}\r\n");
ret.append("window.setInterval(function(){nextFrame(ctx)},").append(rate).append(");\r\n");
ret.append(CanvasShapeExporter.getJsSuffix());
return ret.toString();
}
public static String getJsPrefix() {

View File

@@ -43,8 +43,6 @@ public class DefineBitsJPEG2Tag extends ImageTag implements AloneTag {
public static final int ID = 21;
private SerializableImage cachedImage;
@Override
public int getCharacterId() {
return characterID;
@@ -104,7 +102,7 @@ public class DefineBitsJPEG2Tag extends ImageTag implements AloneTag {
@Override
public void setImage(byte[] data) {
imageData = new ByteArrayRange(data);
cachedImage = null;
clearCache();
setModified(true);
}

View File

@@ -46,8 +46,6 @@ public class DefineBitsJPEG3Tag extends ImageTag implements AloneTag {
public static final int ID = 35;
private SerializableImage cachedImage;
@Override
public int getCharacterId() {
return characterID;
@@ -66,7 +64,7 @@ public class DefineBitsJPEG3Tag extends ImageTag implements AloneTag {
bitmapAlphaData = new byte[0];
}
imageData = new ByteArrayRange(data);
cachedImage = null;
clearCache();
setModified(true);
}

View File

@@ -54,8 +54,6 @@ public class DefineBitsJPEG4Tag extends ImageTag implements AloneTag {
public static final int ID = 90;
private SerializableImage cachedImage;
@Override
public int getCharacterId() {
return characterID;
@@ -83,6 +81,7 @@ public class DefineBitsJPEG4Tag extends ImageTag implements AloneTag {
} else {
bitmapAlphaData = ByteArrayRange.EMPTY;
}
clearCache();
setModified(true);
}

View File

@@ -66,8 +66,6 @@ public class DefineBitsLossless2Tag extends ImageTag implements AloneTag {
public static final int ID = 36;
private SerializableImage cachedImage;
@Override
public int getCharacterId() {
return characterID;
@@ -129,7 +127,7 @@ public class DefineBitsLossless2Tag extends ImageTag implements AloneTag {
sos2.writeBytesZlib(bitmapDataOS.toByteArray());
zlibBitmapData = new ByteArrayRange(zlibOS.toByteArray());
decompressed = false;
cachedImage = null;
clearCache();
setModified(true);
}

View File

@@ -75,8 +75,6 @@ public class DefineBitsLosslessTag extends ImageTag implements AloneTag {
public static final int ID = 20;
private SerializableImage cachedImage;
private byte[] createEmptyImage() {
try {
BITMAPDATA bitmapData = new BITMAPDATA();
@@ -128,7 +126,7 @@ public class DefineBitsLosslessTag extends ImageTag implements AloneTag {
sos2.writeBytesZlib(bitmapDataOS.toByteArray());
zlibBitmapData = new ByteArrayRange(zlibOS.toByteArray());
decompressed = false;
cachedImage = null;
clearCache();
setModified(true);
}

View File

@@ -41,8 +41,6 @@ public class DefineBitsTag extends ImageTag implements TagChangedListener {
public static final int ID = 6;
private SerializableImage cachedImage;
@Override
public void setImage(byte[] data) {
throw new UnsupportedOperationException("Set image is not supported for DefineBits");
@@ -132,6 +130,6 @@ public class DefineBitsTag extends ImageTag implements TagChangedListener {
@Override
public void handleEvent(Tag tag) {
cachedImage = null;
clearCache();
}
}

View File

@@ -432,11 +432,11 @@ public class DefineFont2Tag extends FontTag {
@Override
public String getCharacters(List<Tag> tags) {
String ret = "";
StringBuilder ret = new StringBuilder();
for (int i : codeTable) {
ret += (char) i;
ret.append((char) i);
}
return ret;
return ret.toString();
}
@Override

View File

@@ -435,11 +435,11 @@ public class DefineFont3Tag extends FontTag {
@Override
public String getCharacters(List<Tag> tags) {
String ret = "";
StringBuilder ret = new StringBuilder();
for (int i : codeTable) {
ret += (char) i;
ret.append((char) i);
}
return ret;
return ret.toString();
}
@Override

View File

@@ -319,19 +319,19 @@ public class DefineFontTag extends FontTag {
@Override
public String getCharacters(List<Tag> tags) {
String ret = "";
StringBuilder ret = new StringBuilder();
ensureFontInfo();
if (fontInfoTag != null) {
for (int i : fontInfoTag.codeTable) {
ret += (char) i;
ret.append((char) i);
}
}
if (fontInfo2Tag != null) {
for (int i : fontInfo2Tag.codeTable) {
ret += (char) i;
ret.append((char) i);
}
}
return ret;
return ret.toString();
}
@Override

View File

@@ -127,23 +127,26 @@ public class DefineText2Tag extends TextTag {
@Override
public String getFormattedText() {
FontTag fnt = null;
String ret = "";
ret += "[\r\nxmin " + textBounds.Xmin + "\r\nymin " + textBounds.Ymin + "\r\nxmax " + textBounds.Xmax + "\r\nymax " + textBounds.Ymax;
StringBuilder ret = new StringBuilder();
ret.append("[\r\nxmin ").append(textBounds.Xmin).
append("\r\nymin ").append(textBounds.Ymin).
append("\r\nxmax ").append(textBounds.Xmax).
append("\r\nymax ").append(textBounds.Ymax);
if (textMatrix.translateX != 0) {
ret += "\r\ntranslatex " + textMatrix.translateX;
ret.append("\r\ntranslatex ").append(textMatrix.translateX);
}
if (textMatrix.translateY != 0) {
ret += "\r\ntranslatey " + textMatrix.translateY;
ret.append("\r\ntranslatey ").append(textMatrix.translateY);
}
if (textMatrix.hasScale) {
ret += "\r\nscalex " + textMatrix.scaleX;
ret += "\r\nscaley " + textMatrix.scaleY;
ret.append("\r\nscalex ").append(textMatrix.scaleX);
ret.append("\r\nscaley ").append(textMatrix.scaleY);
}
if (textMatrix.hasRotate) {
ret += "\r\nrotateskew0 " + textMatrix.rotateSkew0;
ret += "\r\nrotateskew1 " + textMatrix.rotateSkew1;
ret.append("\r\nrotateskew0 ").append(textMatrix.rotateSkew0);
ret.append("\r\nrotateskew1 ").append(textMatrix.rotateSkew1);
}
ret += "\r\n]";
ret.append("\r\n]");
for (TEXTRECORD rec : textRecords) {
String params = "";
if (rec.styleFlagsHasFont) {
@@ -167,11 +170,11 @@ public class DefineText2Tag extends TextTag {
params += "\r\ny " + rec.yOffset;
}
if (params.length() > 0) {
ret += "[" + params + "\r\n]";
ret.append("[").append(params).append("\r\n]");
}
ret += Helper.escapeString(rec.getText(fnt)).replace("[", "\\[").replace("]", "\\]");
ret.append(Helper.escapeString(rec.getText(fnt)).replace("[", "\\[").replace("]", "\\]"));
}
return ret;
return ret.toString();
}
@Override

View File

@@ -128,23 +128,26 @@ public class DefineTextTag extends TextTag {
@Override
public String getFormattedText() {
FontTag fnt = null;
String ret = "";
ret += "[\r\nxmin " + textBounds.Xmin + "\r\nymin " + textBounds.Ymin + "\r\nxmax " + textBounds.Xmax + "\r\nymax " + textBounds.Ymax;
StringBuilder ret = new StringBuilder();
ret.append("[\r\nxmin ").append(textBounds.Xmin).
append("\r\nymin ").append(textBounds.Ymin).
append("\r\nxmax ").append(textBounds.Xmax).
append("\r\nymax ").append(textBounds.Ymax);
if (textMatrix.translateX != 0) {
ret += "\r\ntranslatex " + textMatrix.translateX;
ret.append("\r\ntranslatex ").append(textMatrix.translateX);
}
if (textMatrix.translateY != 0) {
ret += "\r\ntranslatey " + textMatrix.translateY;
ret.append("\r\ntranslatey ").append(textMatrix.translateY);
}
if (textMatrix.hasScale) {
ret += "\r\nscalex " + textMatrix.scaleX;
ret += "\r\nscaley " + textMatrix.scaleY;
ret.append("\r\nscalex ").append(textMatrix.scaleX);
ret.append("\r\nscaley ").append(textMatrix.scaleY);
}
if (textMatrix.hasRotate) {
ret += "\r\nrotateskew0 " + textMatrix.rotateSkew0;
ret += "\r\nrotateskew1 " + textMatrix.rotateSkew1;
ret.append("\r\nrotateskew0 ").append(textMatrix.rotateSkew0);
ret.append("\r\nrotateskew1 ").append(textMatrix.rotateSkew1);
}
ret += "\r\n]";
ret.append("\r\n]");
for (TEXTRECORD rec : textRecords) {
String params = "";
if (rec.styleFlagsHasFont) {
@@ -168,16 +171,16 @@ public class DefineTextTag extends TextTag {
params += "\r\ny " + rec.yOffset;
}
if (params.length() > 0) {
ret += "[" + params + "\r\n]";
ret.append("[").append(params).append("\r\n]");
}
if (fnt == null) {
ret += AppResources.translate("fontNotFound").replace("%fontId%", Integer.toString(rec.fontId));
ret.append(AppResources.translate("fontNotFound").replace("%fontId%", Integer.toString(rec.fontId)));
} else {
ret += Helper.escapeString(rec.getText(fnt)).replace("[", "\\[").replace("]", "\\]");
ret.append(Helper.escapeString(rec.getText(fnt)).replace("[", "\\[").replace("]", "\\]"));
}
}
return ret;
return ret.toString();
}
@Override

View File

@@ -50,6 +50,8 @@ import java.util.Set;
*/
public abstract class ImageTag extends CharacterTag implements DrawableTag {
protected SerializableImage cachedImage;
public ImageTag(SWF swf, int id, String name, ByteArrayRange data) {
super(swf, id, name, data);
}
@@ -210,4 +212,8 @@ public abstract class ImageTag extends CharacterTag implements DrawableTag {
public Shape getOutline(int frame, int time, int ratio, DepthState stateUnderCursor, int mouseButton, Matrix transformation) {
return transformation.toTransform().createTransformedShape(getShape().getOutline());
}
public void clearCache() {
cachedImage = null;
}
}

View File

@@ -124,21 +124,16 @@ public final class DefineCompactedFont extends FontTag implements DrawableTag {
shapeCache = fonts.get(0).getGlyphShapes();
}
@Override
public int getNumFrames() {
return 1;
}
@Override
public String getFontNameIntag() {
String ret = "";
StringBuilder ret = new StringBuilder();
for (int i = 0; i < fonts.size(); i++) {
if (i > 0) {
ret += ", ";
ret.append(", ");
}
ret += fonts.get(i).fontName;
ret.append(fonts.get(i).fontName);
}
return ret;
return ret.toString();
}
@Override
@@ -197,7 +192,7 @@ public final class DefineCompactedFont extends FontTag implements DrawableTag {
}
setModified(true);
SWF.clearImageCache();
getSwf().clearImageCache();
}
@Override

View File

@@ -12,7 +12,8 @@
* Lesser General Public License for more details.
*
* You should have received a copy of the GNU Lesser General Public
* License along with this library.
* License along with this library.
*/
package com.jpexs.decompiler.flash.types;
import com.jpexs.decompiler.flash.tags.DefineText2Tag;
@@ -60,10 +61,10 @@ public class TEXTRECORD implements Serializable {
public GLYPHENTRY[] glyphEntries;
public String getText(FontTag font) {
public String getText(FontTag font) {
StringBuilder ret = new StringBuilder();
for (GLYPHENTRY ge : glyphEntries) {
for (GLYPHENTRY ge : glyphEntries) {
ret.append(font.glyphToChar(ge.glyphIndex));
}
}
return ret.toString();
}
}

View File

@@ -12,7 +12,8 @@
* Lesser General Public License for more details.
*
* You should have received a copy of the GNU Lesser General Public
* License along with this library.
* License along with this library.
*/
package com.jpexs.decompiler.graph;
import java.util.Collections;
@@ -34,19 +35,19 @@ public class GraphPartMulti extends GraphPart {
@Override
public String toString() {
public String toString() {
String ret = "";
StringBuilder ret = new StringBuilder();
ret.append("[multi ");
boolean first = true;
for (GraphPart g : parts) {
if (first) {
first = false;
} else {
} else {
ret.append(", ");
}
}
ret.append(g.toString());
}
}
ret += "]";
ret.append("]");
return ret.toString();
}
@Override

View File

@@ -277,7 +277,7 @@ public class Helper {
}
public static String padZeros(long number, int length) {
String ret = "" + number;
String ret = Long.toString(number);
while (ret.length() < length) {
ret = "0" + ret;
}
@@ -330,59 +330,59 @@ public class Helper {
}
public static String joinStrings(List<String> arr, String glue) {
String ret = "";
StringBuilder ret = new StringBuilder();
boolean first = true;
for (String s : arr) {
if (!first) {
ret += glue;
ret.append(glue);
} else {
first = false;
}
ret += s;
ret.append(s);
}
return ret;
return ret.toString();
}
public static String joinStrings(String[] arr, String glue) {
String ret = "";
StringBuilder ret = new StringBuilder();
boolean first = true;
for (String s : arr) {
if (!first) {
ret += glue;
ret.append(glue);
} else {
first = false;
}
ret += s;
ret.append(s);
}
return ret;
return ret.toString();
}
public static String joinStrings(List<String> arr, String formatString, String glue) {
String ret = "";
StringBuilder ret = new StringBuilder();
boolean first = true;
for (String s : arr) {
if (!first) {
ret += glue;
ret.append(glue);
} else {
first = false;
}
ret += String.format(formatString, s);
ret.append(String.format(formatString, s));
}
return ret;
return ret.toString();
}
public static String joinStrings(String[] arr, String formatString, String glue) {
String ret = "";
StringBuilder ret = new StringBuilder();
boolean first = true;
for (String s : arr) {
if (!first) {
ret += glue;
ret.append(glue);
} else {
first = false;
}
ret += String.format(formatString, s);
ret.append(String.format(formatString, s));
}
return ret;
return ret.toString();
}
@SuppressWarnings("unchecked")
@@ -866,7 +866,7 @@ public class Helper {
* @return String
*/
public static String doubleStr(double d) {
String ret = "" + d;
String ret = Double.toString(d);
if (ret.endsWith(".0")) {
ret = ret.substring(0, ret.length() - 2);
}

View File

@@ -178,7 +178,7 @@ public class FontPanel extends javax.swing.JPanel {
}
}
ft.setModified(true);
SWF.clearImageCache();
ft.getSwf().clearImageCache();
}
public void showFontTag(FontTag ft) {

View File

@@ -575,7 +575,7 @@ public final class MainPanel extends JPanel implements ActionListener, TreeSelec
try {
swf.deobfuscateIdentifiers(RenameType.TYPENUMBER);
swf.assignClassesToSymbols();
clearCache();
swf.clearScriptCache();
if (abcPanel != null) {
abcPanel.reload();
}
@@ -1037,15 +1037,6 @@ public final class MainPanel extends JPanel implements ActionListener, TreeSelec
return null;
}
private void clearCache() {
if (abcPanel != null) {
abcPanel.decompiledTextArea.clearScriptCache();
}
if (actionPanel != null) {
actionPanel.clearCache();
}
}
public void gotoFrame(int frame) {
TreeItem treeItem = (TreeItem) tagTree.getLastSelectedPathComponent();
if (treeItem == null) {
@@ -1087,7 +1078,8 @@ public final class MainPanel extends JPanel implements ActionListener, TreeSelec
}
public void disableDecompilationChanged() {
clearCache();
clearAllScriptCache();
if (abcPanel != null) {
abcPanel.reload();
}
@@ -1095,6 +1087,14 @@ public final class MainPanel extends JPanel implements ActionListener, TreeSelec
updateClassesList();
}
private void clearAllScriptCache() {
for (SWFList swfList : swfs) {
for (SWF swf : swfList) {
swf.clearScriptCache();
}
}
}
public void searchAs() {
if (searchDialog == null) {
searchDialog = new SearchDialog(getMainFrame().getWindow());
@@ -1204,7 +1204,7 @@ public final class MainPanel extends JPanel implements ActionListener, TreeSelec
public void autoDeobfuscateChanged() {
Helper.decompilationErrorAdd = AppStrings.translate(Configuration.autoDeobfuscate.get() ? "deobfuscation.comment.failed" : "deobfuscation.comment.tryenable");
clearCache();
clearAllScriptCache();
if (abcPanel != null) {
abcPanel.reload();
}
@@ -1507,7 +1507,7 @@ public final class MainPanel extends JPanel implements ActionListener, TreeSelec
}
}
SWF.clearImageCache();
swf.clearImageCache();
reload(true);
}
}
@@ -1672,7 +1672,7 @@ public final class MainPanel extends JPanel implements ActionListener, TreeSelec
Main.stopWork();
View.showMessageDialog(null, translate("message.rename.renamed").replace("%count%", Integer.toString(cnt)));
swf.assignClassesToSymbols();
clearCache();
swf.clearScriptCache();
if (abcPanel != null) {
abcPanel.reload();
}
@@ -1743,7 +1743,7 @@ public final class MainPanel extends JPanel implements ActionListener, TreeSelec
@Override
public void run() {
clearCache();
clearAllScriptCache();
getABCPanel().reload();
updateClassesList();
}
@@ -1792,7 +1792,7 @@ public final class MainPanel extends JPanel implements ActionListener, TreeSelec
}
public void refreshDecompiled() {
clearCache();
clearAllScriptCache();
if (abcPanel != null) {
abcPanel.reload();
}
@@ -1881,7 +1881,7 @@ public final class MainPanel extends JPanel implements ActionListener, TreeSelec
refreshTree();
setTagTreeSelectedNode(newTag);
}
SWF.clearImageCache();
it.getSwf().clearImageCache();
} catch (IOException ex) {
logger.log(Level.SEVERE, "Invalid image", ex);
View.showMessageDialog(null, translate("error.image.invalid"), translate("error"), JOptionPane.ERROR_MESSAGE);
@@ -1903,7 +1903,7 @@ public final class MainPanel extends JPanel implements ActionListener, TreeSelec
refreshTree();
setTagTreeSelectedNode(newTag);
}
SWF.clearImageCache();
st.getSwf().clearImageCache();
} catch (IOException ex) {
logger.log(Level.SEVERE, "Invalid image", ex);
View.showMessageDialog(null, translate("error.image.invalid"), translate("error"), JOptionPane.ERROR_MESSAGE);

View File

@@ -966,9 +966,10 @@ public class PreviewPanel extends JSplitPane implements ActionListener {
break;
case ACTION_SAVE_GENERIC_TAG: {
genericTagPanel.save();
SWF.clearImageCache();
Tag tag = genericTagPanel.getTag();
tag.getSwf().updateCharacters();
SWF swf = tag.getSwf();
swf.clearImageCache();
swf.updateCharacters();
tag.getTimelined().getTimeline().reset();
mainPanel.refreshTree();
mainPanel.setTagTreeSelectedNode(tag);

View File

@@ -131,7 +131,7 @@ public class TextPanel extends JPanel implements ActionListener {
setEditText(false);
mainPanel.reload(true);
}
SWF.clearImageCache();
item.getSwf().clearImageCache();
}
break;
}

View File

@@ -167,7 +167,8 @@ public class ABCPanel extends JPanel implements ItemListener, ActionListener, Se
pos++;
String workText = AppStrings.translate("work.searching");
String decAdd = "";
if (!decompiledTextArea.isCached(item.getValue())) {
final ScriptPack pack = item.getValue();
if (!SWF.isCached(pack)) {
decAdd = ", " + AppStrings.translate("work.decompiling");
}
@@ -176,10 +177,9 @@ public class ABCPanel extends JPanel implements ItemListener, ActionListener, Se
@Override
public Void doInBackground() throws Exception {
decompiledTextArea.cacheScriptPack(item.getValue(), swf.abcList);
if (pat.matcher(decompiledTextArea.getCachedText(item.getValue())).find()) {
if (pat.matcher(SWF.getCached(pack).text).find()) {
ABCPanelSearchResult searchResult = new ABCPanelSearchResult();
searchResult.scriptPack = item.getValue();
searchResult.scriptPack = pack;
searchResult.classPath = item.getKey();
found.add(searchResult);
}
@@ -644,7 +644,7 @@ public class ABCPanel extends JPanel implements ItemListener, ActionListener, Se
public void reload() {
lastDecompiled = "";
decompiledTextArea.clearScriptCache();
swf.clearScriptCache();
decompiledTextArea.reloadClass();
detailPanel.methodTraitPanel.methodCodePanel.clear();
}
@@ -781,7 +781,7 @@ public class ABCPanel extends JPanel implements ItemListener, ActionListener, Se
case ACTION_SAVE_DECOMPILED:
ScriptPack pack = decompiledTextArea.getScriptLeaf();
int oldIndex = pack.scriptIndex;
decompiledTextArea.uncache(pack);
SWF.uncache(pack);
try {
String oldSp = null;

View File

@@ -16,7 +16,9 @@
*/
package com.jpexs.decompiler.flash.gui.abc;
import com.jpexs.decompiler.flash.SWF;
import com.jpexs.decompiler.flash.abc.ABC;
import com.jpexs.decompiler.flash.abc.CachedDecompilation;
import com.jpexs.decompiler.flash.abc.ScriptPack;
import com.jpexs.decompiler.flash.abc.avm2.AVM2Code;
import com.jpexs.decompiler.flash.abc.avm2.instructions.AVM2Instruction;
@@ -32,17 +34,12 @@ import com.jpexs.decompiler.flash.abc.types.traits.Trait;
import com.jpexs.decompiler.flash.abc.types.traits.TraitFunction;
import com.jpexs.decompiler.flash.abc.types.traits.TraitMethodGetterSetter;
import com.jpexs.decompiler.flash.abc.types.traits.TraitSlotConst;
import com.jpexs.decompiler.flash.configuration.Configuration;
import com.jpexs.decompiler.flash.exporters.modes.ScriptExportMode;
import com.jpexs.decompiler.flash.gui.AppStrings;
import com.jpexs.decompiler.flash.gui.View;
import com.jpexs.decompiler.flash.helpers.HighlightedText;
import com.jpexs.decompiler.flash.helpers.HighlightedTextWriter;
import com.jpexs.decompiler.flash.helpers.hilight.HighlightData;
import com.jpexs.decompiler.flash.helpers.hilight.HighlightSpecialType;
import com.jpexs.decompiler.flash.helpers.hilight.Highlighting;
import com.jpexs.decompiler.flash.tags.ABCContainerTag;
import com.jpexs.helpers.Cache;
import java.awt.Point;
import java.util.ArrayList;
import java.util.List;
@@ -72,7 +69,6 @@ public class DecompiledEditorPane extends LineMarkedEditorPane implements CaretL
private final ABCPanel abcPanel;
private int classIndex = -1;
private boolean isStatic = false;
private final Cache<ScriptPack, CachedDecompilation> cache = Cache.getInstance(true);
private final List<Runnable> scriptListeners = new ArrayList<>();
@@ -583,25 +579,6 @@ public class DecompiledEditorPane extends LineMarkedEditorPane implements CaretL
}
}
public void uncache(ScriptPack pack) {
cache.remove(pack);
}
public boolean isCached(ScriptPack pack) {
return cache.contains(pack);
}
private CachedDecompilation getCached(ScriptPack pack) throws InterruptedException {
if (!cache.contains(pack)) {
cacheScriptPack(pack, abcList);
}
return (CachedDecompilation) cache.get(pack);
}
public String getCachedText(ScriptPack pack) throws InterruptedException {
return getCached(pack).text;
}
public void gotoLastTrait() {
gotoTrait(lastTraitIndex);
}
@@ -647,27 +624,6 @@ public class DecompiledEditorPane extends LineMarkedEditorPane implements CaretL
}
private List<ABCContainerTag> abcList;
public void clearScriptCache() {
cache.clear();
}
public void cacheScriptPack(ScriptPack scriptLeaf, List<ABCContainerTag> abcList) throws InterruptedException {
int maxCacheSize = 50;
int scriptIndex = scriptLeaf.scriptIndex;
ScriptInfo script = null;
ABC abc = scriptLeaf.abc;
if (scriptIndex > -1) {
script = abc.script_info.get(scriptIndex);
}
if (!cache.contains(scriptLeaf)) {
boolean parallel = Configuration.parallelSpeedUp.get();
HighlightedTextWriter writer = new HighlightedTextWriter(Configuration.getCodeFormatting(), true);
scriptLeaf.toSource(writer, abcList, script.traits.traits, ScriptExportMode.AS, parallel);
HighlightedText hilightedCode = new HighlightedText(writer);
cache.put(scriptLeaf, new CachedDecompilation(hilightedCode));
}
}
public void setScript(ScriptPack scriptLeaf, List<ABCContainerTag> abcList) {
abcPanel.scriptNameLabel.setText(scriptLeaf.getClassPath().toString());
int scriptIndex = scriptLeaf.scriptIndex;
@@ -691,8 +647,7 @@ public class DecompiledEditorPane extends LineMarkedEditorPane implements CaretL
this.script = scriptLeaf;
CachedDecompilation cd = null;
try {
cacheScriptPack(scriptLeaf, abcList);
cd = getCached(scriptLeaf);
cd = SWF.getCached(scriptLeaf);
} catch (InterruptedException ex) {
}
if (cd != null) {
@@ -710,7 +665,7 @@ public class DecompiledEditorPane extends LineMarkedEditorPane implements CaretL
public void reloadClass() {
int ci = classIndex;
uncache(script);
SWF.uncache(script);
if ((script != null) && (abc != null)) {
setScript(script, abcList);
}
@@ -724,7 +679,6 @@ public class DecompiledEditorPane extends LineMarkedEditorPane implements CaretL
public void setABC(ABC abc) {
this.abc = abc;
cache.clear();
setText("");
}

View File

@@ -21,6 +21,7 @@ import com.jpexs.decompiler.flash.SWF;
import com.jpexs.decompiler.flash.action.Action;
import com.jpexs.decompiler.flash.action.ActionGraph;
import com.jpexs.decompiler.flash.action.ActionList;
import com.jpexs.decompiler.flash.action.CachedScript;
import com.jpexs.decompiler.flash.action.parser.ActionParseException;
import com.jpexs.decompiler.flash.action.parser.pcode.ASMParser;
import com.jpexs.decompiler.flash.action.parser.script.ActionScriptLexer;
@@ -48,7 +49,6 @@ import com.jpexs.decompiler.flash.helpers.hilight.Highlighting;
import com.jpexs.decompiler.flash.tags.base.ASMSource;
import com.jpexs.decompiler.graph.CompilationException;
import com.jpexs.decompiler.graph.GraphTargetItem;
import com.jpexs.helpers.Cache;
import com.jpexs.helpers.CancellableWorker;
import com.jpexs.helpers.Helper;
import java.awt.BorderLayout;
@@ -129,7 +129,6 @@ public class ActionPanel extends JPanel implements ActionListener, SearchListene
private String lastDecompiled = "";
private ASMSource lastASM;
public SearchPanel<ActionSearchResult> searchPanel;
private Cache<ASMSource, CachedScript> cache = Cache.getInstance(true);
private CancellableWorker setSourceWorker;
public void clearSource() {
@@ -143,10 +142,6 @@ public class ActionPanel extends JPanel implements ActionListener, SearchListene
srcHexOnly = null;
}
public void clearCache() {
cache.clear();
}
public String getStringUnderCursor() {
int pos = decompiledEditor.getCaretPosition();
@@ -213,27 +208,6 @@ public class ActionPanel extends JPanel implements ActionListener, SearchListene
return null;
}
private CachedScript getCached(ASMSource pack) {
return (CachedScript) cache.get(pack);
}
private boolean isCached(ASMSource src) {
return cache.contains(src);
}
private void cacheScript(ASMSource src, List<Action> actions) throws InterruptedException {
if (!cache.contains(src)) {
if (actions == null) {
actions = src.getActions();
}
HighlightedTextWriter writer = new HighlightedTextWriter(Configuration.getCodeFormatting(), true);
Action.actionsToSource(src, actions, src.toString()/*FIXME?*/, writer);
List<Highlighting> hilights = writer.instructionHilights;
String srcNoHex = writer.toString();
cache.put(src, new CachedScript(srcNoHex, hilights));
}
}
public boolean search(final String txt, boolean ignoreCase, boolean regexp) {
if ((txt != null) && (!txt.isEmpty())) {
searchPanel.setOptions(ignoreCase, regexp);
@@ -251,18 +225,18 @@ public class ActionPanel extends JPanel implements ActionListener, SearchListene
pos++;
String workText = AppStrings.translate("work.searching");
String decAdd = "";
if (!isCached(item.getValue())) {
ASMSource asm = item.getValue();
if (!SWF.isCached(asm)) {
decAdd = ", " + AppStrings.translate("work.decompiling");
}
Main.startWork(workText + " \"" + txt + "\"" + decAdd + " - (" + pos + "/" + asms.size() + ") " + item.getKey() + "... ");
try {
cacheScript(item.getValue(), null);
if (pat.matcher(SWF.getCached(asm, null).text).find()) {
found.add(new ActionSearchResult(asm, item.getKey()));
}
} catch (InterruptedException ex) {
break;
}
if (pat.matcher(getCached(item.getValue()).text).find()) {
found.add(new ActionSearchResult(item.getValue(), item.getKey()));
}
}
Main.stopWork();
@@ -434,10 +408,9 @@ public class ActionPanel extends JPanel implements ActionListener, SearchListene
if (Configuration.decompile.get()) {
setDecompiledText("//" + AppStrings.translate("work.decompiling") + "...");
if (!useCache) {
uncache(asm);
SWF.uncache(asm);
}
cacheScript(asm, actions);
CachedScript sc = getCached(asm);
CachedScript sc = SWF.getCached(asm, actions);
decompiledHilights = sc.hilights;
lastDecompiled = sc.text;
lastASM = asm;
@@ -830,8 +803,4 @@ public class ActionPanel extends JPanel implements ActionListener, SearchListene
}
});
}
private void uncache(ASMSource pack) {
cache.remove(pack);
}
}

View File

@@ -288,10 +288,13 @@ public class TagTreeContextMenu extends JPopupMenu implements ActionListener {
@Override
public void actionPerformed(ActionEvent ae) {
tag.getSwf().tags.remove(tag);
SWF sourceSwf = tag.getSwf();
sourceSwf.tags.remove(tag);
tag.setSwf(targetSwf);
targetSwf.tags.add(tag);
tag.setModified(true);
sourceSwf.clearImageCache();
targetSwf.clearImageCache();
mainPanel.refreshTree();
}
});