diff options
Diffstat (limited to 'dx/src/com/android/dx/cf/code/Machine.java')
-rw-r--r-- | dx/src/com/android/dx/cf/code/Machine.java | 208 |
1 files changed, 208 insertions, 0 deletions
diff --git a/dx/src/com/android/dx/cf/code/Machine.java b/dx/src/com/android/dx/cf/code/Machine.java new file mode 100644 index 0000000..72ba3b4 --- /dev/null +++ b/dx/src/com/android/dx/cf/code/Machine.java @@ -0,0 +1,208 @@ +/* + * Copyright (C) 2007 The Android Open Source Project + * + * 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 com.android.dx.cf.code; + +import com.android.dx.rop.cst.Constant; +import com.android.dx.rop.type.Prototype; +import com.android.dx.rop.type.Type; +import com.android.dx.rop.code.LocalItem; +import java.util.ArrayList; + +/** + * Interface for machines capable of executing bytecode by acting + * upon a {@link Frame}. A machine conceptually contains four arbitrary-value + * argument slots, slots for several literal-value arguments, and slots for + * branch target information. + */ +public interface Machine { + /** + * Gets the effective prototype of the method that this instance is + * being used for. The <i>effective</i> prototype includes an initial + * {@code this} argument for instance methods. + * + * @return {@code non-null;} the method prototype + */ + public Prototype getPrototype(); + + /** + * Clears the regular and auxiliary arguments area. + */ + public void clearArgs(); + + /** + * Pops the given number of values from the stack (of either category), + * and store them in the arguments area, indicating that there are now + * that many arguments. Also, clear the auxiliary arguments. + * + * @param frame {@code non-null;} frame to operate on + * @param count {@code >= 0;} number of values to pop + */ + public void popArgs(Frame frame, int count); + + /** + * Pops values from the stack of the types indicated by the given + * {@code Prototype} (popped in reverse of the argument + * order, so the first prototype argument type is for the deepest + * element of the stack), and store them in the arguments area, + * indicating that there are now that many arguments. Also, clear + * the auxiliary arguments. + * + * @param frame {@code non-null;} frame to operate on + * @param prototype {@code non-null;} prototype indicating arguments to pop + */ + public void popArgs(Frame frame, Prototype prototype); + + /** + * Pops a value from the stack of the indicated type, and store it + * in the arguments area, indicating that there are now that many + * arguments. Also, clear the auxiliary arguments. + * + * @param frame {@code non-null;} frame to operate on + * @param type {@code non-null;} type of the argument + */ + public void popArgs(Frame frame, Type type); + + /** + * Pops values from the stack of the indicated types (popped in + * reverse argument order, so the first indicated type is for the + * deepest element of the stack), and store them in the arguments + * area, indicating that there are now that many arguments. Also, + * clear the auxiliary arguments. + * + * @param frame {@code non-null;} frame to operate on + * @param type1 {@code non-null;} type of the first argument + * @param type2 {@code non-null;} type of the second argument + */ + public void popArgs(Frame frame, Type type1, Type type2); + + /** + * Pops values from the stack of the indicated types (popped in + * reverse argument order, so the first indicated type is for the + * deepest element of the stack), and store them in the arguments + * area, indicating that there are now that many arguments. Also, + * clear the auxiliary arguments. + * + * @param frame {@code non-null;} frame to operate on + * @param type1 {@code non-null;} type of the first argument + * @param type2 {@code non-null;} type of the second argument + * @param type3 {@code non-null;} type of the third argument + */ + public void popArgs(Frame frame, Type type1, Type type2, Type type3); + + /** + * Loads the local variable with the given index as the sole argument in + * the arguments area. Also, clear the auxiliary arguments. + * + * @param frame {@code non-null;} frame to operate on + * @param idx {@code >= 0;} the local variable index + */ + public void localArg(Frame frame, int idx); + + /** + * Indicates that the salient type of this operation is as + * given. This differentiates between, for example, the various + * arithmetic opcodes, which, by the time they hit a + * {@code Machine} are collapsed to the {@code int} + * variant. (See {@link BytecodeArray#parseInstruction} for + * details.) + * + * @param type {@code non-null;} the salient type of the upcoming operation + */ + public void auxType(Type type); + + /** + * Indicates that there is an auxiliary (inline, not stack) + * argument of type {@code int}, with the given value. + * + * <p><b>Note:</b> Perhaps unintuitively, the stack manipulation + * ops (e.g., {@code dup} and {@code swap}) use this to + * indicate the result stack pattern with a straightforward hex + * encoding of the push order starting with least-significant + * nibbles getting pushed first). For example, an all-category-1 + * {@code dup2_x1} sets this to {@code 0x12312}, and the + * other form of that op sets this to + * {@code 0x121}.</p> + * + * <p><b>Also Note:</b> For {@code switch*} instructions, this is + * used to indicate the padding value (which is only useful for + * verification).</p> + * + * @param value the argument value + */ + public void auxIntArg(int value); + + /** + * Indicates that there is an auxiliary (inline, not stack) object + * argument, with the value based on the given constant. + * + * <p><b>Note:</b> Some opcodes use both {@code int} and + * constant auxiliary arguments.</p> + * + * @param cst {@code non-null;} the constant containing / referencing + * the value + */ + public void auxCstArg(Constant cst); + + /** + * Indicates that there is an auxiliary (inline, not stack) argument + * indicating a branch target. + * + * @param target the argument value + */ + public void auxTargetArg(int target); + + /** + * Indicates that there is an auxiliary (inline, not stack) argument + * consisting of a {@code switch*} table. + * + * <p><b>Note:</b> This is generally used in conjunction with + * {@link #auxIntArg} (which holds the padding).</p> + * + * @param cases {@code non-null;} the list of key-target pairs, plus the default + * target + */ + public void auxSwitchArg(SwitchList cases); + + /** + * Indicates that there is an auxiliary (inline, not stack) argument + * consisting of a list of initial values for a newly created array. + * + * @param initValues {@code non-null;} the list of constant values to initialize + * the array + */ + public void auxInitValues(ArrayList<Constant> initValues); + + /** + * Indicates that the target of this operation is the given local. + * + * @param idx {@code >= 0;} the local variable index + * @param type {@code non-null;} the type of the local + * @param local {@code null-ok;} the name and signature of the local, if known + */ + public void localTarget(int idx, Type type, LocalItem local); + + /** + * "Runs" the indicated opcode in an appropriate way, using the arguments + * area as appropriate, and modifying the given frame in response. + * + * @param frame {@code non-null;} frame to operate on + * @param offset {@code >= 0;} byte offset in the method to the opcode being + * run + * @param opcode {@code >= 0;} the opcode to run + */ + public void run(Frame frame, int offset, int opcode); +} |