proguard.classfile.editor.InstructionSequencesReplacer Maven / Gradle / Ivy
Go to download
Show more of this group Show more artifacts with this name
Show all versions of proguard-core Show documentation
Show all versions of proguard-core Show documentation
ProGuardCORE is a free library to read, analyze, modify, and write Java class files.
/*
* ProGuardCORE -- library to process Java bytecode.
*
* Copyright (c) 2002-2020 Guardsquare NV
*
* 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 proguard.classfile.editor;
import proguard.classfile.constant.Constant;
import proguard.classfile.instruction.Instruction;
import proguard.classfile.instruction.visitor.*;
import proguard.classfile.util.BranchTargetFinder;
/**
* This {@link InstructionVisitor} replaces multiple instruction sequences at once.
*
* The replacement sequences are optional, defaulting to the empty sequence,
* to delete the matched pattern sequences.
*
* @see InstructionSequenceReplacer
* @author Eric Lafortune
*/
public class InstructionSequencesReplacer
extends MultiInstructionVisitor
implements InstructionVisitor
{
private static final int PATTERN_INDEX = 0;
private static final int REPLACEMENT_INDEX = 1;
private static final Instruction[] EMPTY_INSTRUCTIONS = new Instruction[0];
/**
* Creates a new InstructionSequencesReplacer.
* @param constants any constants referenced by the pattern
* instructions and replacement instructions.
* @param instructionSequences the instruction sequences to be replaced,
* with subsequently the sequence pair index,
* the patten/replacement index (0 or 1),
* and the instruction index in the sequence.
* @param branchTargetFinder a branch target finder that has been
* initialized to indicate branch targets
* in the visited code.
* @param codeAttributeEditor a code editor that can be used for
* accumulating changes to the code.
*/
public InstructionSequencesReplacer(Constant[] constants,
Instruction[][][] instructionSequences,
BranchTargetFinder branchTargetFinder,
CodeAttributeEditor codeAttributeEditor)
{
this(constants,
instructionSequences,
branchTargetFinder,
codeAttributeEditor,
null);
}
/**
* Creates a new InstructionSequenceReplacer.
* @param constants any constants referenced by the pattern
* instructions and replacement instructions.
* @param instructionSequences the instruction sequences to be replaced,
* with subsequently the sequence pair index,
* the patten/replacement index (0 or 1),
* and the instruction index in the sequence.
* @param branchTargetFinder a branch target finder that has been
* initialized to indicate branch targets
* in the visited code.
* @param codeAttributeEditor a code editor that can be used for
* accumulating changes to the code.
* @param extraInstructionVisitor an optional extra visitor for all deleted
* load instructions.
*/
public InstructionSequencesReplacer(Constant[] constants,
Instruction[][][] instructionSequences,
BranchTargetFinder branchTargetFinder,
CodeAttributeEditor codeAttributeEditor,
InstructionVisitor extraInstructionVisitor)
{
super(createInstructionSequenceReplacers(constants,
instructionSequences,
branchTargetFinder,
codeAttributeEditor,
extraInstructionVisitor));
}
/**
* Creates an array of InstructionSequenceReplacer instances.
* @param constants any constants referenced by the pattern
* instructions and replacement instructions.
* @param instructionSequences the instruction sequences to be replaced,
* with subsequently the sequence pair index,
* the from/to index (0 or 1), and the
* instruction index in the sequence.
* @param branchTargetFinder a branch target finder that has been
* initialized to indicate branch targets
* in the visited code.
* @param codeAttributeEditor a code editor that can be used for
* accumulating changes to the code.
* @param extraInstructionVisitor an optional extra visitor for all deleted
* load instructions.
*/
private static InstructionVisitor[] createInstructionSequenceReplacers(Constant[] constants,
Instruction[][][] instructionSequences,
BranchTargetFinder branchTargetFinder,
CodeAttributeEditor codeAttributeEditor,
InstructionVisitor extraInstructionVisitor)
{
InstructionVisitor[] instructionSequenceReplacers =
new InstructionVisitor[instructionSequences.length];
for (int index = 0; index < instructionSequenceReplacers.length; index++)
{
Instruction[][] instructionSequencePair =
instructionSequences[index];
Instruction[] patternInstructions =
instructionSequencePair[PATTERN_INDEX];
// The replacement sequence is optional.
Instruction[] replacementInstructions =
instructionSequencePair.length > REPLACEMENT_INDEX ?
instructionSequencePair[REPLACEMENT_INDEX] :
EMPTY_INSTRUCTIONS;
instructionSequenceReplacers[index] =
new InstructionSequenceReplacer(constants,
patternInstructions,
constants,
replacementInstructions,
branchTargetFinder,
codeAttributeEditor,
extraInstructionVisitor);
}
return instructionSequenceReplacers;
}
}
© 2015 - 2025 Weber Informatics LLC | Privacy Policy