mirror of
https://github.com/revanced/Apktool.git
synced 2024-08-28 18:16:41 +02:00
Merge ResAttrDecoder into the AXmlResourceParser (#3243)
This commit is contained in:
parent
9d7d58016e
commit
0a354a9d97
@ -19,10 +19,15 @@ package brut.androlib.res.decoder;
|
|||||||
import android.content.res.XmlResourceParser;
|
import android.content.res.XmlResourceParser;
|
||||||
import android.util.TypedValue;
|
import android.util.TypedValue;
|
||||||
import brut.androlib.exceptions.AndrolibException;
|
import brut.androlib.exceptions.AndrolibException;
|
||||||
|
import brut.androlib.exceptions.CantFindFrameworkResException;
|
||||||
|
import brut.androlib.exceptions.UndefinedResObjectException;
|
||||||
import brut.androlib.res.data.ResID;
|
import brut.androlib.res.data.ResID;
|
||||||
|
import brut.androlib.res.data.ResResSpec;
|
||||||
import brut.androlib.res.data.ResTable;
|
import brut.androlib.res.data.ResTable;
|
||||||
import brut.androlib.res.data.arsc.ARSCHeader;
|
import brut.androlib.res.data.arsc.ARSCHeader;
|
||||||
import brut.androlib.res.data.axml.NamespaceStack;
|
import brut.androlib.res.data.axml.NamespaceStack;
|
||||||
|
import brut.androlib.res.data.value.ResAttr;
|
||||||
|
import brut.androlib.res.data.value.ResScalarValue;
|
||||||
import brut.androlib.res.xml.ResXmlEncoders;
|
import brut.androlib.res.xml.ResXmlEncoders;
|
||||||
import brut.util.ExtCountingDataInput;
|
import brut.util.ExtCountingDataInput;
|
||||||
import com.google.common.io.LittleEndianDataInputStream;
|
import com.google.common.io.LittleEndianDataInputStream;
|
||||||
@ -44,20 +49,16 @@ import java.util.logging.Logger;
|
|||||||
public class AXmlResourceParser implements XmlResourceParser {
|
public class AXmlResourceParser implements XmlResourceParser {
|
||||||
|
|
||||||
public AXmlResourceParser(ResTable resTable) {
|
public AXmlResourceParser(ResTable resTable) {
|
||||||
|
mResTable = resTable;
|
||||||
resetEventInfo();
|
resetEventInfo();
|
||||||
setAttrDecoder(new ResAttrDecoder(resTable));
|
|
||||||
}
|
}
|
||||||
|
|
||||||
public AndrolibException getFirstError() {
|
public AndrolibException getFirstError() {
|
||||||
return mFirstError;
|
return mFirstError;
|
||||||
}
|
}
|
||||||
|
|
||||||
public ResAttrDecoder getAttrDecoder() {
|
public ResTable getResTable() {
|
||||||
return mAttrDecoder;
|
return mResTable;
|
||||||
}
|
|
||||||
|
|
||||||
public void setAttrDecoder(ResAttrDecoder attrDecoder) {
|
|
||||||
mAttrDecoder = attrDecoder;
|
|
||||||
}
|
}
|
||||||
|
|
||||||
public void open(InputStream stream) {
|
public void open(InputStream stream) {
|
||||||
@ -298,6 +299,19 @@ public class AXmlResourceParser implements XmlResourceParser {
|
|||||||
return value;
|
return value;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
public String decodeFromResourceId(int attrResId) throws AndrolibException {
|
||||||
|
if (attrResId != 0) {
|
||||||
|
try {
|
||||||
|
ResResSpec resResSpec = mResTable.getResSpec(attrResId);
|
||||||
|
if (resResSpec != null) {
|
||||||
|
return resResSpec.getName();
|
||||||
|
}
|
||||||
|
} catch (UndefinedResObjectException | CantFindFrameworkResException ignored) {}
|
||||||
|
}
|
||||||
|
|
||||||
|
return null;
|
||||||
|
}
|
||||||
|
|
||||||
private String getNonDefaultNamespaceUri(int offset) {
|
private String getNonDefaultNamespaceUri(int offset) {
|
||||||
String prefix = mStringBlock.getString(mNamespaces.getPrefix(offset));
|
String prefix = mStringBlock.getString(mNamespaces.getPrefix(offset));
|
||||||
if (prefix != null) {
|
if (prefix != null) {
|
||||||
@ -337,7 +351,7 @@ public class AXmlResourceParser implements XmlResourceParser {
|
|||||||
int resourceId = getAttributeNameResource(index);
|
int resourceId = getAttributeNameResource(index);
|
||||||
|
|
||||||
try {
|
try {
|
||||||
resourceMapValue = mAttrDecoder.decodeFromResourceId(resourceId);
|
resourceMapValue = decodeFromResourceId(resourceId);
|
||||||
} catch (AndrolibException ignored) {
|
} catch (AndrolibException ignored) {
|
||||||
resourceMapValue = null;
|
resourceMapValue = null;
|
||||||
}
|
}
|
||||||
@ -389,7 +403,6 @@ public class AXmlResourceParser implements XmlResourceParser {
|
|||||||
int valueData = mAttributes[offset + ATTRIBUTE_IX_VALUE_DATA];
|
int valueData = mAttributes[offset + ATTRIBUTE_IX_VALUE_DATA];
|
||||||
int valueRaw = mAttributes[offset + ATTRIBUTE_IX_VALUE_STRING];
|
int valueRaw = mAttributes[offset + ATTRIBUTE_IX_VALUE_STRING];
|
||||||
|
|
||||||
if (mAttrDecoder != null) {
|
|
||||||
try {
|
try {
|
||||||
String stringBlockValue = valueRaw == -1 ? null : ResXmlEncoders.escapeXmlChars(mStringBlock.getString(valueRaw));
|
String stringBlockValue = valueRaw == -1 ? null : ResXmlEncoders.escapeXmlChars(mStringBlock.getString(valueRaw));
|
||||||
String resourceMapValue = null;
|
String resourceMapValue = null;
|
||||||
@ -398,7 +411,7 @@ public class AXmlResourceParser implements XmlResourceParser {
|
|||||||
// spam lookups against resource table for invalid ids.
|
// spam lookups against resource table for invalid ids.
|
||||||
if (valueType == TypedValue.TYPE_REFERENCE || valueType == TypedValue.TYPE_DYNAMIC_REFERENCE ||
|
if (valueType == TypedValue.TYPE_REFERENCE || valueType == TypedValue.TYPE_DYNAMIC_REFERENCE ||
|
||||||
valueType == TypedValue.TYPE_ATTRIBUTE || valueType == TypedValue.TYPE_DYNAMIC_ATTRIBUTE) {
|
valueType == TypedValue.TYPE_ATTRIBUTE || valueType == TypedValue.TYPE_DYNAMIC_ATTRIBUTE) {
|
||||||
resourceMapValue = mAttrDecoder.decodeFromResourceId(valueData);
|
resourceMapValue = decodeFromResourceId(valueData);
|
||||||
}
|
}
|
||||||
String value = stringBlockValue;
|
String value = stringBlockValue;
|
||||||
|
|
||||||
@ -417,12 +430,22 @@ public class AXmlResourceParser implements XmlResourceParser {
|
|||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
return mAttrDecoder.decode(
|
// try to decode from resource table
|
||||||
valueType,
|
int attrResId = getAttributeNameResource(index);
|
||||||
valueData,
|
ResScalarValue resValue = mResTable.getCurrentResPackage()
|
||||||
value,
|
.getValueFactory().factory(valueType, valueData, value);
|
||||||
getAttributeNameResource(index)
|
|
||||||
);
|
String decoded = null;
|
||||||
|
if (attrResId > 0) {
|
||||||
|
try {
|
||||||
|
ResAttr attr = (ResAttr) mResTable.getResSpec(attrResId).getDefaultResource().getValue();
|
||||||
|
|
||||||
|
decoded = attr.convertToResXmlFormat(resValue);
|
||||||
|
} catch (UndefinedResObjectException | ClassCastException ignored) {}
|
||||||
|
}
|
||||||
|
|
||||||
|
return decoded != null ? decoded : resValue.encodeAsResXmlAttr();
|
||||||
|
|
||||||
} catch (AndrolibException ex) {
|
} catch (AndrolibException ex) {
|
||||||
setFirstError(ex);
|
setFirstError(ex);
|
||||||
LOGGER.log(Level.WARNING, String.format("Could not decode attr value, using undecoded value "
|
LOGGER.log(Level.WARNING, String.format("Could not decode attr value, using undecoded value "
|
||||||
@ -431,7 +454,6 @@ public class AXmlResourceParser implements XmlResourceParser {
|
|||||||
getAttributeName(index),
|
getAttributeName(index),
|
||||||
valueData), ex);
|
valueData), ex);
|
||||||
}
|
}
|
||||||
}
|
|
||||||
return TypedValue.coerceToString(valueType, valueData);
|
return TypedValue.coerceToString(valueType, valueData);
|
||||||
}
|
}
|
||||||
|
|
||||||
@ -801,7 +823,7 @@ public class AXmlResourceParser implements XmlResourceParser {
|
|||||||
}
|
}
|
||||||
|
|
||||||
private ExtCountingDataInput mIn;
|
private ExtCountingDataInput mIn;
|
||||||
private ResAttrDecoder mAttrDecoder;
|
private final ResTable mResTable;
|
||||||
private AndrolibException mFirstError;
|
private AndrolibException mFirstError;
|
||||||
|
|
||||||
private boolean isOperational = false;
|
private boolean isOperational = false;
|
||||||
|
@ -1,74 +0,0 @@
|
|||||||
/*
|
|
||||||
* Copyright (C) 2010 Ryszard Wiśniewski <brut.alll@gmail.com>
|
|
||||||
* Copyright (C) 2010 Connor Tumbleson <connor.tumbleson@gmail.com>
|
|
||||||
*
|
|
||||||
* Licensed under the Apache License, Version 2.0 (the "License");
|
|
||||||
* you may not use this file except in compliance with the License.
|
|
||||||
* You may obtain a copy of the License at
|
|
||||||
*
|
|
||||||
* https://www.apache.org/licenses/LICENSE-2.0
|
|
||||||
*
|
|
||||||
* Unless required by applicable law or agreed to in writing, software
|
|
||||||
* distributed under the License is distributed on an "AS IS" BASIS,
|
|
||||||
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
|
|
||||||
* See the License for the specific language governing permissions and
|
|
||||||
* limitations under the License.
|
|
||||||
*/
|
|
||||||
package brut.androlib.res.decoder;
|
|
||||||
|
|
||||||
import brut.androlib.exceptions.AndrolibException;
|
|
||||||
import brut.androlib.exceptions.CantFindFrameworkResException;
|
|
||||||
import brut.androlib.exceptions.UndefinedResObjectException;
|
|
||||||
import brut.androlib.res.data.ResID;
|
|
||||||
import brut.androlib.res.data.ResResSpec;
|
|
||||||
import brut.androlib.res.data.ResTable;
|
|
||||||
import brut.androlib.res.data.value.ResAttr;
|
|
||||||
import brut.androlib.res.data.value.ResScalarValue;
|
|
||||||
|
|
||||||
public class ResAttrDecoder {
|
|
||||||
|
|
||||||
public ResAttrDecoder(ResTable resTable) {
|
|
||||||
mResTable = resTable;
|
|
||||||
}
|
|
||||||
|
|
||||||
public String decode(int type, int value, String rawValue, int attrResId) throws AndrolibException {
|
|
||||||
ResScalarValue resValue = mResTable.getCurrentResPackage().getValueFactory().factory(type, value, rawValue);
|
|
||||||
|
|
||||||
String decoded = null;
|
|
||||||
if (attrResId > 0) {
|
|
||||||
try {
|
|
||||||
ResAttr attr = (ResAttr) mResTable.getResSpec(attrResId).getDefaultResource().getValue();
|
|
||||||
|
|
||||||
decoded = attr.convertToResXmlFormat(resValue);
|
|
||||||
} catch (UndefinedResObjectException | ClassCastException ignored) {}
|
|
||||||
}
|
|
||||||
|
|
||||||
return decoded != null ? decoded : resValue.encodeAsResXmlAttr();
|
|
||||||
}
|
|
||||||
|
|
||||||
public String decodeFromResourceId(int attrResId) throws AndrolibException {
|
|
||||||
if (attrResId != 0) {
|
|
||||||
try {
|
|
||||||
ResResSpec resResSpec = mResTable.getResSpec(attrResId);
|
|
||||||
if (resResSpec != null) {
|
|
||||||
return resResSpec.getName();
|
|
||||||
}
|
|
||||||
} catch (UndefinedResObjectException | CantFindFrameworkResException ignored) {}
|
|
||||||
}
|
|
||||||
|
|
||||||
return null;
|
|
||||||
}
|
|
||||||
|
|
||||||
public ResTable getResTable() throws AndrolibException {
|
|
||||||
if (mResTable == null) {
|
|
||||||
throw new AndrolibException("Res Table not set");
|
|
||||||
}
|
|
||||||
return mResTable;
|
|
||||||
}
|
|
||||||
|
|
||||||
public void setResTable(ResTable resTable) {
|
|
||||||
mResTable = resTable;
|
|
||||||
}
|
|
||||||
|
|
||||||
private ResTable mResTable;
|
|
||||||
}
|
|
@ -31,7 +31,7 @@ import org.xmlpull.v1.wrapper.classic.StaticXmlSerializerWrapper;
|
|||||||
import java.io.*;
|
import java.io.*;
|
||||||
|
|
||||||
public class XmlPullStreamDecoder implements ResStreamDecoder {
|
public class XmlPullStreamDecoder implements ResStreamDecoder {
|
||||||
public XmlPullStreamDecoder(XmlPullParser parser,
|
public XmlPullStreamDecoder(AXmlResourceParser parser,
|
||||||
ExtXmlSerializer serializer) {
|
ExtXmlSerializer serializer) {
|
||||||
this.mParser = parser;
|
this.mParser = parser;
|
||||||
this.mSerial = serializer;
|
this.mSerial = serializer;
|
||||||
@ -43,7 +43,7 @@ public class XmlPullStreamDecoder implements ResStreamDecoder {
|
|||||||
try {
|
try {
|
||||||
XmlPullWrapperFactory factory = XmlPullWrapperFactory.newInstance();
|
XmlPullWrapperFactory factory = XmlPullWrapperFactory.newInstance();
|
||||||
XmlPullParserWrapper par = factory.newPullParserWrapper(mParser);
|
XmlPullParserWrapper par = factory.newPullParserWrapper(mParser);
|
||||||
final ResTable resTable = ((AXmlResourceParser) mParser).getAttrDecoder().getResTable();
|
final ResTable resTable = mParser.getResTable();
|
||||||
|
|
||||||
XmlSerializerWrapper ser = new StaticXmlSerializerWrapper(mSerial, factory) {
|
XmlSerializerWrapper ser = new StaticXmlSerializerWrapper(mSerial, factory) {
|
||||||
boolean hideSdkInfo = false;
|
boolean hideSdkInfo = false;
|
||||||
@ -149,6 +149,6 @@ public class XmlPullStreamDecoder implements ResStreamDecoder {
|
|||||||
decode(in, out);
|
decode(in, out);
|
||||||
}
|
}
|
||||||
|
|
||||||
private final XmlPullParser mParser;
|
private final AXmlResourceParser mParser;
|
||||||
private final ExtXmlSerializer mSerial;
|
private final ExtXmlSerializer mSerial;
|
||||||
}
|
}
|
||||||
|
Loading…
Reference in New Issue
Block a user