Synchronize access to ClassFileAnalysisState

This commit is contained in:
caheckman
2020-07-29 17:03:46 -04:00
parent 9c2ce9b395
commit 93039d3958
3 changed files with 32 additions and 25 deletions

View File

@@ -19,6 +19,8 @@ import java.io.IOException;
import ghidra.app.plugin.processors.sleigh.PcodeEmit; import ghidra.app.plugin.processors.sleigh.PcodeEmit;
import ghidra.app.plugin.processors.sleigh.SleighLanguage; import ghidra.app.plugin.processors.sleigh.SleighLanguage;
import ghidra.javaclass.format.ClassFileAnalysisState;
import ghidra.javaclass.format.ClassFileJava;
import ghidra.javaclass.format.constantpool.AbstractConstantPoolInfoJava; import ghidra.javaclass.format.constantpool.AbstractConstantPoolInfoJava;
import ghidra.program.model.lang.InjectContext; import ghidra.program.model.lang.InjectContext;
import ghidra.program.model.lang.InjectPayload; import ghidra.program.model.lang.InjectPayload;
@@ -42,15 +44,15 @@ public abstract class InjectPayloadJava implements InjectPayload {
} }
protected static AbstractConstantPoolInfoJava[] getConstantPool(Program program) { protected static AbstractConstantPoolInfoJava[] getConstantPool(Program program) {
ConstantPoolJava cPool = null; ClassFileAnalysisState analysisState;
try { try {
cPool = new ConstantPoolJava(program); analysisState = ClassFileAnalysisState.getState(program);
} }
catch (IOException e) { catch (IOException e) {
// TODO Auto-generated catch block return null;
e.printStackTrace();
} }
return cPool.getConstantPool(); ClassFileJava classFile = analysisState.getClassFile();
return classFile.getConstantPool();
} }
@Override @Override

View File

@@ -1,3 +1,18 @@
/* ###
* IP: GHIDRA
*
* 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
*
* http://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 ghidra.app.util.pcodeInject; package ghidra.app.util.pcodeInject;
import java.util.ArrayList; import java.util.ArrayList;

View File

@@ -39,7 +39,6 @@ public class ClassFileAnalysisState implements AnalysisState {
private Program program; private Program program;
private ClassFileJava classFile; // Constant-pool and method descriptions private ClassFileJava classFile; // Constant-pool and method descriptions
private UniqueAddressFactory uniqueFactory; // Produces temporary registers during p-code generation
private HashMap<Address, MethodInfoJava> methodMap; // Map from address to method description private HashMap<Address, MethodInfoJava> methodMap; // Map from address to method description
public ClassFileAnalysisState(Program program) throws IOException { public ClassFileAnalysisState(Program program) throws IOException {
@@ -53,8 +52,6 @@ public class ClassFileAnalysisState implements AnalysisState {
MemoryByteProvider provider = new MemoryByteProvider(memory, space); MemoryByteProvider provider = new MemoryByteProvider(memory, space);
BinaryReader reader = new BinaryReader(provider, false); BinaryReader reader = new BinaryReader(provider, false);
classFile = new ClassFileJava(reader); classFile = new ClassFileJava(reader);
uniqueFactory =
new UniqueAddressFactory(program.getAddressFactory(), program.getLanguage());
} }
/** /**
@@ -70,27 +67,20 @@ public class ClassFileAnalysisState implements AnalysisState {
* @return the MethodInfoJava describing the method, or null if no method is found at the address * @return the MethodInfoJava describing the method, or null if no method is found at the address
*/ */
public MethodInfoJava getMethodInfo(Address addr) { public MethodInfoJava getMethodInfo(Address addr) {
if (methodMap == null) { synchronized (this) {
try { if (methodMap == null) {
buildMethodMap(); try {
} buildMethodMap();
catch (MemoryAccessException e) { }
Msg.error(this, e.getMessage(), e); catch (MemoryAccessException e) {
// methodMap will be non-null but empty Msg.error(this, e.getMessage(), e);
// methodMap will be non-null but empty
}
} }
} }
return methodMap.get(addr); return methodMap.get(addr);
} }
/**
* Generate (the address of) a new temporary register, for use when resolving injections
* during p-code generation for a Java instruction
* @return the address of the next available temporary register
*/
public Address getNextUniqueAddress() {
return uniqueFactory.getNextUniqueAddress();
}
/** /**
* Walk through the {@link MethodInfoJava} objects in {@link ClassFileJava} and * Walk through the {@link MethodInfoJava} objects in {@link ClassFileJava} and
* create a map from Address to the corresponding object * create a map from Address to the corresponding object
@@ -114,7 +104,7 @@ public class ClassFileAnalysisState implements AnalysisState {
* @param program * @param program
* @return <code>ClassFileAnalysisState</code> for specified program instance * @return <code>ClassFileAnalysisState</code> for specified program instance
*/ */
public static ClassFileAnalysisState getState(Program program) throws IOException { public static synchronized ClassFileAnalysisState getState(Program program) throws IOException {
ClassFileAnalysisState analysisState = ClassFileAnalysisState analysisState =
AnalysisStateInfo.getAnalysisState(program, ClassFileAnalysisState.class); AnalysisStateInfo.getAnalysisState(program, ClassFileAnalysisState.class);
if (analysisState == null) { if (analysisState == null) {