⭐ 欢迎来到虫虫下载站! | 📦 资源下载 📁 资源专辑 ℹ️ 关于我们
⭐ 虫虫下载站

📄 partialevaluator.java

📁 j2me 混淆包,用于混淆j2me的原代码用的
💻 JAVA
📖 第 1 页 / 共 5 页
字号:
                                       int lowestNecessaryIndex)    {        return branchOrigin <= lowestNecessaryIndex ^               branchTarget <= lowestNecessaryIndex;    }    /**     * Inserts pop instructions where necessary, in order to make sure the     * stack is consistent at the given index.     * @param classFile    the class file that is being checked.     * @param codeAttrInfo the code that is being checked.     * @param index        the offset of the dependent instruction.     */    private void fixStackConsistency(ClassFile    classFile,                                     CodeAttrInfo codeAttrInfo,                                     int          index)    {        // Is the unnecessary instruction popping values (but not a dup/swap        // instruction)?        Instruction popInstruction = InstructionFactory.create(codeAttrInfo.code,                                                               index);        byte popOpcode = popInstruction.opcode;        int popCount = popInstruction.stackPopCount(classFile);        if (popCount > 0) // &&            //popOpcode != InstructionConstants.OP_DUP     &&            //popOpcode != InstructionConstants.OP_DUP_X1  &&            //popOpcode != InstructionConstants.OP_DUP_X2  &&            //popOpcode != InstructionConstants.OP_DUP2    &&            //popOpcode != InstructionConstants.OP_DUP2_X1 &&            //popOpcode != InstructionConstants.OP_DUP2_X2 &&            //popOpcode != InstructionConstants.OP_SWAP)        {            // Check the instructions on which it depends.            InstructionOffsetValue traceOffsetValue = stackTraceValues[index];            int traceOffsetCount = traceOffsetValue.instructionOffsetCount();            if (popCount <= 4 &&                isAllNecessary(traceOffsetValue))            {                if (popOpcode == InstructionConstants.OP_POP ||                    popOpcode == InstructionConstants.OP_POP2)                {                    if (DEBUG_ANALYSIS) System.out.println("  Popping value again at "+popInstruction.toString(index)+" (pushed at all "+traceOffsetValue.instructionOffsetCount()+" offsets)");                    // Simply mark pop and pop2 instructions.                    isNecessary[index] = true;                }                else                {                    if (DEBUG_ANALYSIS) System.out.println("  Popping value instead of "+popInstruction.toString(index)+" (pushed at all "+traceOffsetValue.instructionOffsetCount()+" offsets)");                    // Make sure the pushed value is popped again,                    // right before this instruction.                    decreaseStackSize(index, popCount, true, true);                }            }            //else if (popCount == (popInstruction.isCategory2() ? 4 : 2) &&            //         traceOffsetCount == 2                              &&            //         isAnyNecessary(traceOffsetValue))            //{            //    if (DEBUG_ANALYSIS) System.out.println("  Popping single value instead of "+popInstruction.toString(index)+" (pushed at some of "+traceOffsetValue.instructionOffsetCount()+" offsets)");            //            //    // Make sure the single pushed value is popped again,            //    // right before this instruction.            //    decreaseStackSize(index, popCount / 2, true, true);            //}            else if (isAnyNecessary(traceOffsetValue))            {                if (DEBUG_ANALYSIS) System.out.println("  Popping value somewhere before "+index+" (pushed at some of "+traceOffsetValue.instructionOffsetCount()+" offsets):");                // Go over all stack pushing instructions.                for (int traceOffsetIndex = 0; traceOffsetIndex < traceOffsetCount; traceOffsetIndex++)                {                    // Has the push instruction been marked?                    int pushInstructionOffset = traceOffsetValue.instructionOffset(traceOffsetIndex);                    if (isNecessary[pushInstructionOffset])                    {                        Instruction pushInstruction = InstructionFactory.create(codeAttrInfo.code,                                                                                pushInstructionOffset);                        int lastOffset = lastPopInstructionOffset(pushInstructionOffset,                                                                  index,                                                                  pushInstructionOffset);                        if (DEBUG_ANALYSIS) System.out.println("    Popping value right after "+lastOffset+", due to push at "+pushInstructionOffset);                        // Make sure the pushed value is popped again,                        // right after the instruction that pushes it                        // (or after the dup instruction that still uses it).                        decreaseStackSize(lastOffset,                                          pushInstruction.stackPushCount(classFile),                                          false, false);                    }                }            }        }    }    /**     * Returns the last offset of the necessary instruction that depends on the     * stack result of the instruction at the given index.     * @param startOffset           the start offset in the search.     * @param endOffset             the end offset in the search.     * @param pushInstructionOffset the offset of the instruction that pushes     *                              a result onto the stack.     * @return the last offset of the necessary instruction that uses the     *         above result.     */    private int lastPopInstructionOffset(int startOffset,                                         int endOffset,                                         int pushInstructionOffset)    {        int lastOffset = startOffset;        for (int index = startOffset; index < endOffset; index++)        {            if (isNecessary[index] &&                stackTraceValues[index].contains(pushInstructionOffset))            {                lastOffset = index;            }        }        return lastOffset;    }    /**     * Puts the required push instruction before the given index. The     * instruction is marked as necessary.     * @param index             the offset of the instruction.     * @param computationalType the computational type on the stack, for     *                          push instructions.     * @param delete            specifies whether the instruction should be     *                          deleted.     */    private void increaseStackSize(int     index,                                   int     computationalType,                                   boolean delete)    {        // Mark this instruction.        isNecessary[index] = true;        // Create a simple push instrucion.        byte replacementOpcode =            computationalType == Value.TYPE_INTEGER   ? InstructionConstants.OP_ICONST_0    :            computationalType == Value.TYPE_LONG      ? InstructionConstants.OP_LCONST_0    :            computationalType == Value.TYPE_FLOAT     ? InstructionConstants.OP_FCONST_0    :            computationalType == Value.TYPE_DOUBLE    ? InstructionConstants.OP_DCONST_0    :            computationalType == Value.TYPE_REFERENCE ? InstructionConstants.OP_ACONST_NULL :                                                        InstructionConstants.OP_NOP;        Instruction replacementInstruction = new SimpleInstruction(replacementOpcode);        // Insert the pop or push instruction.        codeAttrInfoEditor.insertBeforeInstruction(index,                                                   replacementInstruction);        // Delete the original instruction if necessary.        if (delete)        {            codeAttrInfoEditor.deleteInstruction(index);        }    }    /**     * Puts the required pop instruction at the given index. The     * instruction is marked as necessary.     * @param offset   the offset of the instruction.     * @param popCount the required reduction of the stack size.     * @param before   specifies whether the pop instruction should be inserted     *                 before or after the present instruction.     * @param delete   specifies whether the instruction should be deleted.     */    private void decreaseStackSize(int     offset,                                   int     popCount,                                   boolean before,                                   boolean delete)    {        boolean after = !before;        // Special case: we may replace the instruction by two pop instructions.        if (delete && popCount > 2)        {            before = true;            after  = true;        }        if (popCount < 1 ||            popCount > 4)        {            throw new IllegalArgumentException("Unsupported stack size reduction ["+popCount+"]");        }        // Mark this instruction.        isNecessary[offset] = true;        if (before)        {            // Create a simple pop instrucion.            byte replacementOpcode = popCount == 1 || popCount == 3 ?                InstructionConstants.OP_POP :                InstructionConstants.OP_POP2;            Instruction replacementInstruction = new SimpleInstruction(replacementOpcode);            // Insert the pop instruction.            codeAttrInfoEditor.insertBeforeInstruction(offset,                                                       replacementInstruction);        }        if (after)        {            // Create a simple pop instrucion.            byte replacementOpcode = popCount == 1 ?                InstructionConstants.OP_POP :                InstructionConstants.OP_POP2;            Instruction replacementInstruction = new SimpleInstruction(replacementOpcode);            if (DEBUG_ANALYSIS) System.out.println("    Pop instruction after ["+offset+"]: "+replacementInstruction);             // Insert the pop instruction.            codeAttrInfoEditor.insertAfterInstruction(offset,                                                      replacementInstruction);        }        // Delete the original instruction if necessary.        if (delete)        {            codeAttrInfoEditor.deleteInstruction(offset);        }    }    /**     * Replaces the specified instruction by the proper dup/swap variant,     * if necessary, depending on the state of the stack.     * @param codeAttrInfo the code that is being checked.     * @param offset       the offset of the instruction.     */    private void fixDupInstruction(CodeAttrInfo codeAttrInfo,                                   int          offset)    {        byte replacementOpcode = 0;        // Simplify the popping instruction if possible.        switch (codeAttrInfo.code[offset])        {            case InstructionConstants.OP_DUP_X1:                if (!isStackEntryPresent(offset, 1))                {                    replacementOpcode = InstructionConstants.OP_DUP;                }                break;            case InstructionConstants.OP_DUP_X2:                if (!isStackEntryPresent(offset, 1) ||                    !isStackEntryPresent(offset, 2))                {                    if (isStackEntryPresent(offset, 1) ||                        isStackEntryPresent(offset, 2))                    {                        replacementOpcode = InstructionConstants.OP_DUP_X1;                    }                    else                    {                        replacementOpcode = InstructionConstants.OP_DUP;                    }                }                break;            case InstructionConstants.OP_DUP2_X1:                if (!isStackEntryPresent(offset, 2))                {                    replacementOpcode = InstructionConstants.OP_DUP2;                }                break;            case InstructionConstants.OP_DUP2_X2:                if (!isStackEntryPresent(offset, 2) ||                    !isStackEntryPresent(offset, 3))                {                    if (isStackEntryPresent(offset, 2) ||                        isStackEntryPresent(offset, 3))                    {                        replacementOpcode = InstructionConstants.OP_DUP2_X1;                    }                    else                    {                        replacementOpcode = InstructionConstants.OP_DUP2;                    }                }                break;            case InstructionConstants.OP_SWAP:                if (!isStackEntryPresent(offset, 0))                {                    isNecessary[offset] = false;

⌨️ 快捷键说明

复制代码 Ctrl + C
搜索代码 Ctrl + F
全屏模式 F11
切换主题 Ctrl + Shift + D
显示快捷键 ?
增大字号 Ctrl + =
减小字号 Ctrl + -