Search in sources :

Example 31 with InternalTranslationException

use of com.google.security.zynamics.reil.translators.InternalTranslationException in project binnavi by google.

the class AddressingModeTwoGenerator method generate.

public static Pair<String, String> generate(final long baseOffset, final ITranslationEnvironment environment, final IInstruction instruction, final List<ReilInstruction> instructions, final IOperandTreeNode rootNode) throws InternalTranslationException {
    Preconditions.checkNotNull(environment, "Error: Argument environment can't be null");
    Preconditions.checkNotNull(instruction, "Error: Argument instruction can't be null");
    Preconditions.checkNotNull(instructions, "Error: Argument instructions can't be null");
    /**
     * parse the OperandTree to see what type of operand we received
     *
     *  This code is very verbose right now and due to this fact if a Bug is found in one type of
     * the functions be sure to check both other functions if they are OK
     *
     */
    if (rootNode.getChildren().get(0).getValue().equals("!")) {
        // matched pre- indexed
        if ((rootNode.getChildren().get(0).getChildren().get(0).getChildren().get(0).getChildren().get(0).getType() == ExpressionType.REGISTER) && (rootNode.getChildren().get(0).getChildren().get(0).getChildren().get(0).getChildren().get(1).getType() == ExpressionType.IMMEDIATE_INTEGER)) {
            // matched [ Rn , #imm ]!
            return preIndexedImm(baseOffset, environment, instructions, rootNode.getChildren().get(0).getChildren().get(0).getChildren().get(0).getChildren().get(0).getValue(), rootNode.getChildren().get(0).getChildren().get(0).getChildren().get(0).getChildren().get(1).getValue());
        } else if ((rootNode.getChildren().get(0).getChildren().get(0).getChildren().get(0).getChildren().get(0).getType() == ExpressionType.REGISTER) && (rootNode.getChildren().get(0).getChildren().get(0).getChildren().get(0).getChildren().get(1).getType() == ExpressionType.REGISTER)) {
            // matched [ Rn, Rm ]!
            return preIndexedReg(baseOffset, environment, instructions, (rootNode.getChildren().get(0).getChildren().get(0).getChildren().get(0).getChildren().get(0).getValue()), (rootNode.getChildren().get(0).getChildren().get(0).getChildren().get(0).getChildren().get(1).getValue()));
        } else {
            // matched [ Rn, Rm, <shift>, #imm ]!
            if (rootNode.getChildren().get(0).getChildren().get(0).getChildren().get(0).getChildren().get(1).getValue().equals("LSL")) {
                return preIndexedLSL(baseOffset, environment, instructions, (rootNode.getChildren().get(0).getChildren().get(0).getChildren().get(0).getChildren().get(0).getValue()), (rootNode.getChildren().get(0).getChildren().get(0).getChildren().get(0).getChildren().get(1).getChildren().get(0).getValue()), (rootNode.getChildren().get(0).getChildren().get(0).getChildren().get(0).getChildren().get(1).getChildren().get(1).getValue()));
            } else if (rootNode.getChildren().get(0).getChildren().get(0).getChildren().get(0).getChildren().get(1).getValue().equals("LSR")) {
                return preIndexedLSR(baseOffset, environment, instructions, (rootNode.getChildren().get(0).getChildren().get(0).getChildren().get(0).getChildren().get(0).getValue()), (rootNode.getChildren().get(0).getChildren().get(0).getChildren().get(0).getChildren().get(1).getChildren().get(0).getValue()), (rootNode.getChildren().get(0).getChildren().get(0).getChildren().get(0).getChildren().get(1).getChildren().get(1).getValue()));
            } else if (rootNode.getChildren().get(0).getChildren().get(0).getChildren().get(0).getChildren().get(1).getValue().equals("ASR")) {
                return preIndexedASR(baseOffset, environment, instructions, (rootNode.getChildren().get(0).getChildren().get(0).getChildren().get(0).getChildren().get(0).getValue()), (rootNode.getChildren().get(0).getChildren().get(0).getChildren().get(0).getChildren().get(1).getChildren().get(0).getValue()), (rootNode.getChildren().get(0).getChildren().get(0).getChildren().get(0).getChildren().get(1).getChildren().get(1).getValue()));
            } else if (rootNode.getChildren().get(0).getChildren().get(0).getChildren().get(0).getChildren().get(1).getValue().equals("ROR")) {
                return preIndexedROR(baseOffset, environment, instructions, (rootNode.getChildren().get(0).getChildren().get(0).getChildren().get(0).getChildren().get(0).getValue()), (rootNode.getChildren().get(0).getChildren().get(0).getChildren().get(0).getChildren().get(1).getChildren().get(0).getValue()), (rootNode.getChildren().get(0).getChildren().get(0).getChildren().get(0).getChildren().get(1).getChildren().get(1).getValue()));
            } else if (rootNode.getChildren().get(0).getChildren().get(0).getChildren().get(0).getChildren().get(1).getValue().equals("RRX")) {
                return preIndexedRRX(baseOffset, environment, instructions, (rootNode.getChildren().get(0).getChildren().get(0).getChildren().get(0).getChildren().get(0).getValue()), (rootNode.getChildren().get(0).getChildren().get(0).getChildren().get(0).getChildren().get(1).getChildren().get(0).getValue()));
            } else {
                throw new InternalTranslationException("Error: AddressOperandTypeTwo preIndexed shifter is not valid");
            }
        }
    } else if (rootNode.getChildren().get(0).getValue().equals(",")) {
        // matched post- indexed
        if ((rootNode.getChildren().get(0).getChildren().get(0).getChildren().get(0).getType() == ExpressionType.REGISTER) && (rootNode.getChildren().get(0).getChildren().get(1).getType() == ExpressionType.IMMEDIATE_INTEGER)) {
            // matched [ Rn ], #imm
            return postIndexedImm(baseOffset, environment, instructions, (rootNode.getChildren().get(0).getChildren().get(0).getChildren().get(0).getValue()), (rootNode.getChildren().get(0).getChildren().get(1).getValue()));
        } else if ((rootNode.getChildren().get(0).getChildren().get(0).getChildren().get(0).getType() == ExpressionType.REGISTER) && (rootNode.getChildren().get(0).getChildren().get(1).getType() == ExpressionType.REGISTER)) {
            // matched [ Rn ], Rm
            return postIndexedReg(baseOffset, environment, instructions, (rootNode.getChildren().get(0).getChildren().get(0).getChildren().get(0).getValue()), (rootNode.getChildren().get(0).getChildren().get(1).getValue()));
        } else {
            // matched [ Rn ], Rm, <shift>, #imm
            if (rootNode.getChildren().get(0).getChildren().get(1).getValue().equals("LSL")) {
                return postIndexedLSL(baseOffset, environment, instructions, (rootNode.getChildren().get(0).getChildren().get(0).getChildren().get(0).getValue()), (rootNode.getChildren().get(0).getChildren().get(1).getChildren().get(0).getValue()), (rootNode.getChildren().get(0).getChildren().get(1).getChildren().get(1).getValue()));
            } else if (rootNode.getChildren().get(0).getChildren().get(1).getValue().equals("LSR")) {
                return postIndexedLSR(baseOffset, environment, instructions, (rootNode.getChildren().get(0).getChildren().get(0).getChildren().get(0).getValue()), (rootNode.getChildren().get(0).getChildren().get(1).getChildren().get(0).getValue()), (rootNode.getChildren().get(0).getChildren().get(1).getChildren().get(1).getValue()));
            } else if (rootNode.getChildren().get(0).getChildren().get(1).getValue().equals("ASR")) {
                return postIndexedASR(baseOffset, environment, instructions, (rootNode.getChildren().get(0).getChildren().get(0).getChildren().get(0).getValue()), (rootNode.getChildren().get(0).getChildren().get(1).getChildren().get(0).getValue()), (rootNode.getChildren().get(0).getChildren().get(1).getChildren().get(1).getValue()));
            } else if (rootNode.getChildren().get(0).getChildren().get(1).getValue().equals("ROR")) {
                return postIndexedROR(baseOffset, environment, instructions, (rootNode.getChildren().get(0).getChildren().get(0).getChildren().get(0).getValue()), (rootNode.getChildren().get(0).getChildren().get(1).getChildren().get(0).getValue()), (rootNode.getChildren().get(0).getChildren().get(1).getChildren().get(1).getValue()));
            } else if (rootNode.getChildren().get(0).getChildren().get(1).getValue().equals("RRX")) {
                return postIndexedRRX(baseOffset, environment, instructions, (rootNode.getChildren().get(0).getChildren().get(0).getChildren().get(0).getValue()), (rootNode.getChildren().get(0).getChildren().get(1).getChildren().get(0).getValue()));
            } else {
                throw new InternalTranslationException("Error: AddressOperandTypeTwo postIndexed shifter is not valid");
            }
        }
    } else if (rootNode.getChildren().get(0).getValue().equals("[")) {
        // matched offset
        if (rootNode.getChildren().get(0).getChildren().get(0).getType() == ExpressionType.IMMEDIATE_INTEGER) {
            return new Pair<String, String>(rootNode.getChildren().get(0).getChildren().get(0).getValue(), "");
        } else if (rootNode.getChildren().get(0).getChildren().get(0).getType() == ExpressionType.REGISTER) {
            return new Pair<String, String>((rootNode.getChildren().get(0).getChildren().get(0).getValue()), "");
        } else if ((rootNode.getChildren().get(0).getChildren().get(0).getChildren().get(0).getType() == ExpressionType.REGISTER) && (rootNode.getChildren().get(0).getChildren().get(0).getChildren().get(1).getType() == ExpressionType.IMMEDIATE_INTEGER)) {
            // matched [ Rn , #imm ]
            return offsetImm(baseOffset, environment, instructions, (rootNode.getChildren().get(0).getChildren().get(0).getChildren().get(0).getValue()), (rootNode.getChildren().get(0).getChildren().get(0).getChildren().get(1).getValue()));
        } else if ((rootNode.getChildren().get(0).getChildren().get(0).getChildren().get(0).getType() == ExpressionType.REGISTER) && (rootNode.getChildren().get(0).getChildren().get(0).getChildren().get(1).getType() == ExpressionType.REGISTER)) {
            // matched [ Rn , Rm ]
            return offsetReg(baseOffset, environment, instructions, (rootNode.getChildren().get(0).getChildren().get(0).getChildren().get(0).getValue()), (rootNode.getChildren().get(0).getChildren().get(0).getChildren().get(1).getValue()));
        } else {
            // matched [ Rn , Rm, <shift>, #imm ]
            if (rootNode.getChildren().get(0).getChildren().get(0).getChildren().get(1).getValue().equals("LSL")) {
                return offsetLSL(baseOffset, environment, instructions, (rootNode.getChildren().get(0).getChildren().get(0).getChildren().get(0).getValue()), (rootNode.getChildren().get(0).getChildren().get(0).getChildren().get(1).getChildren().get(0).getValue()), (rootNode.getChildren().get(0).getChildren().get(0).getChildren().get(1).getChildren().get(1).getValue()));
            } else if (rootNode.getChildren().get(0).getChildren().get(0).getChildren().get(1).getValue().equals("LSR")) {
                return offsetLSR(baseOffset, environment, instructions, (rootNode.getChildren().get(0).getChildren().get(0).getChildren().get(0).getValue()), (rootNode.getChildren().get(0).getChildren().get(0).getChildren().get(1).getChildren().get(0).getValue()), (rootNode.getChildren().get(0).getChildren().get(0).getChildren().get(1).getChildren().get(1).getValue()));
            } else if (rootNode.getChildren().get(0).getChildren().get(0).getChildren().get(1).getValue().equals("ASR")) {
                return offsetASR(baseOffset, environment, instructions, (rootNode.getChildren().get(0).getChildren().get(0).getChildren().get(0).getValue()), (rootNode.getChildren().get(0).getChildren().get(0).getChildren().get(1).getChildren().get(0).getValue()), (rootNode.getChildren().get(0).getChildren().get(0).getChildren().get(1).getChildren().get(1).getValue()));
            } else if (rootNode.getChildren().get(0).getChildren().get(0).getChildren().get(1).getValue().equals("ROR")) {
                return offsetROR(baseOffset, environment, instructions, (rootNode.getChildren().get(0).getChildren().get(0).getChildren().get(0).getValue()), (rootNode.getChildren().get(0).getChildren().get(0).getChildren().get(1).getChildren().get(0).getValue()), (rootNode.getChildren().get(0).getChildren().get(0).getChildren().get(1).getChildren().get(1).getValue()));
            } else if (rootNode.getChildren().get(0).getChildren().get(0).getChildren().get(1).getValue().equals("RRX")) {
                return offsetRRX(baseOffset, environment, instructions, (rootNode.getChildren().get(0).getChildren().get(0).getChildren().get(0).getValue()), (rootNode.getChildren().get(0).getChildren().get(0).getChildren().get(1).getChildren().get(0).getValue()));
            } else {
                throw new InternalTranslationException("Error: AddressOperandTypeTwo offset shifter is not valid");
            }
        }
    } else {
        throw new InternalTranslationException("Error: AddressOperandTypeTwo rootNodeValue is not valid " + rootNode.getChildren().get(0).getValue() + " " + instruction.getMnemonic());
    }
}
Also used : InternalTranslationException(com.google.security.zynamics.reil.translators.InternalTranslationException) Pair(com.google.security.zynamics.zylib.general.Pair)

Example 32 with InternalTranslationException

use of com.google.security.zynamics.reil.translators.InternalTranslationException in project binnavi by google.

the class RolTranslator method translate.

// TODO(timkornau): Check this code again
/**
   * Translates a ROL instruction to REIL code.
   *
   * @param environment A valid translation environment.
   * @param instruction The ROL instruction to translate.
   * @param instructions The generated REIL code will be added to this list
   *
   * @throws InternalTranslationException if any of the arguments are null the passed instruction is
   *         not an ROL instruction
   */
@Override
public void translate(final ITranslationEnvironment environment, final IInstruction instruction, final List<ReilInstruction> instructions) throws InternalTranslationException {
    TranslationHelpers.checkTranslationArguments(environment, instruction, instructions, "rol");
    if (instruction.getOperands().size() != 2) {
        throw new InternalTranslationException("Error: Argument instruction is not a rol instruction (invalid number of operand)");
    }
    final long baseOffset = instruction.getAddress().toLong() * 0x100;
    long offset = baseOffset;
    final List<? extends IOperandTree> operands = instruction.getOperands();
    final IOperandTree targetOperand = operands.get(0);
    final IOperandTree sourceOperand = operands.get(1);
    // Load source operand.
    final TranslationResult sourceResult = Helpers.translateOperand(environment, offset, sourceOperand, true);
    instructions.addAll(sourceResult.getInstructions());
    // Adjust the offset of the next REIL instruction.
    offset = baseOffset + instructions.size();
    // Load target operand.
    final TranslationResult targetResult = Helpers.translateOperand(environment, offset, targetOperand, true);
    instructions.addAll(targetResult.getInstructions());
    // Adjust the offset of the next REIL instruction.
    offset = baseOffset + instructions.size();
    final OperandSize sourceSize = sourceResult.getSize();
    final OperandSize targetSize = targetResult.getSize();
    final String sourceRegister = sourceResult.getRegister();
    final String targetRegister = targetResult.getRegister();
    final String rotateMask = environment.getNextVariableString();
    final String rotateMaskZero = environment.getNextVariableString();
    final String rotateMaskLessOne = environment.getNextVariableString();
    final String rotateMaskOne = environment.getNextVariableString();
    final String shrValue = environment.getNextVariableString();
    final String shredResult = environment.getNextVariableString();
    final String shledResult = environment.getNextVariableString();
    final String result = environment.getNextVariableString();
    final String tempOf = environment.getNextVariableString();
    final String tempOfLsb = environment.getNextVariableString();
    final String msbMask = String.valueOf(TranslationHelpers.getMsbMask(targetSize));
    final String modVal = String.valueOf(targetSize.getBitSize());
    final String shiftMsbLsb = String.valueOf(TranslationHelpers.getShiftMsbLsbMask(targetSize));
    final int linesBefore = instructions.size();
    // Make sure to rotate less than the size of the register
    instructions.add(ReilHelpers.createMod(offset, sourceSize, sourceRegister, targetSize, modVal, targetSize, rotateMask));
    // Find out if the rotate mask is 0 and negate the result
    instructions.add(ReilHelpers.createBisz(offset + 1, targetSize, rotateMask, OperandSize.BYTE, rotateMaskZero));
    // Find out if the rotate mask is 1
    instructions.add(ReilHelpers.createSub(offset + 2, targetSize, rotateMask, targetSize, "1", targetSize, rotateMaskLessOne));
    instructions.add(ReilHelpers.createBisz(offset + 3, targetSize, rotateMaskLessOne, OperandSize.BYTE, rotateMaskOne));
    // Perform the rotate
    instructions.add(ReilHelpers.createBsh(offset + 4, targetSize, targetRegister, OperandSize.BYTE, rotateMask, targetSize, shledResult));
    instructions.add(ReilHelpers.createAdd(offset + 5, OperandSize.BYTE, "-" + modVal, OperandSize.BYTE, rotateMask, OperandSize.BYTE, shrValue));
    instructions.add(ReilHelpers.createBsh(offset + 6, targetSize, targetRegister, OperandSize.BYTE, shrValue, targetSize, shredResult));
    instructions.add(ReilHelpers.createOr(offset + 7, targetSize, shledResult, targetSize, shredResult, targetSize, result));
    // Don't change the flags if the rotate value was zero
    final String jmpGoal = String.format("%d.%d", instruction.getAddress().toLong(), linesBefore + 16);
    instructions.add(ReilHelpers.createJcc(offset + 8, OperandSize.BYTE, rotateMaskZero, OperandSize.ADDRESS, jmpGoal));
    // Set the CF to the new LSB
    instructions.add(ReilHelpers.createAnd(offset + 9, targetSize, result, sourceSize, "1", OperandSize.BYTE, Helpers.CARRY_FLAG));
    // The OF needs to be set to a different value if the rotate-mask was 1
    final String jmpGoal2 = String.format("%d.%d", instruction.getAddress().toLong(), linesBefore + 13);
    instructions.add(ReilHelpers.createJcc(offset + 10, OperandSize.BYTE, rotateMaskOne, OperandSize.ADDRESS, jmpGoal2));
    // Set the OF to undefined if the rotate-mask was positive but not 1
    instructions.add(ReilHelpers.createUndef(offset + 11, OperandSize.BYTE, Helpers.OVERFLOW_FLAG));
    // Jump to the end
    final String jmpGoal3 = String.format("%d.%d", instruction.getAddress().toLong(), linesBefore + 16);
    instructions.add(ReilHelpers.createJcc(offset + 12, OperandSize.BYTE, "1", OperandSize.ADDRESS, jmpGoal3));
    // OF = MSB(DEST) XOR CF
    instructions.add(ReilHelpers.createAnd(offset + 13, targetSize, result, targetSize, msbMask, sourceSize, tempOf));
    instructions.add(ReilHelpers.createBsh(offset + 14, targetSize, tempOf, targetSize, shiftMsbLsb, OperandSize.BYTE, tempOfLsb));
    instructions.add(ReilHelpers.createBsh(offset + 15, OperandSize.BYTE, tempOfLsb, OperandSize.BYTE, Helpers.CARRY_FLAG, OperandSize.BYTE, Helpers.OVERFLOW_FLAG));
    Helpers.writeBack(environment, offset + 16, targetOperand, result, targetResult.getSize(), targetResult.getAddress(), targetResult.getType(), instructions);
}
Also used : IOperandTree(com.google.security.zynamics.zylib.disassembly.IOperandTree) InternalTranslationException(com.google.security.zynamics.reil.translators.InternalTranslationException) TranslationResult(com.google.security.zynamics.reil.translators.TranslationResult) OperandSize(com.google.security.zynamics.reil.OperandSize)

Example 33 with InternalTranslationException

use of com.google.security.zynamics.reil.translators.InternalTranslationException in project binnavi by google.

the class RorTranslator method translate.

// TODO(timkornau): Check this code again
/**
   * Translates a ROR instruction to REIL code.
   *
   * @param environment A valid translation environment.
   * @param instruction The ROR instruction to translate.
   * @param instructions The generated REIL code will be added to this list
   *
   * @throws InternalTranslationException if any of the arguments are null the
   *           passed instruction is not an ROR instruction
   */
@Override
public void translate(final ITranslationEnvironment environment, final IInstruction instruction, final List<ReilInstruction> instructions) throws InternalTranslationException {
    if (instruction.getOperands().size() != 2) {
        throw new InternalTranslationException("Error: Argument instruction is not a ror instruction (invalid number of operands)");
    }
    final long baseOffset = instruction.getAddress().toLong() * 0x100;
    long offset = baseOffset;
    final List<? extends IOperandTree> operands = instruction.getOperands();
    final IOperandTree targetOperand = operands.get(0);
    final IOperandTree sourceOperand = operands.get(1);
    // Load source operand.
    final TranslationResult sourceResult = Helpers.translateOperand(environment, offset, sourceOperand, true);
    instructions.addAll(sourceResult.getInstructions());
    // Adjust the offset of the next REIL instruction.
    offset = baseOffset + instructions.size();
    // Load destination operand.
    final TranslationResult targetResult = Helpers.translateOperand(environment, offset, targetOperand, true);
    instructions.addAll(targetResult.getInstructions());
    // Adjust the offset of the next REIL instruction.
    offset = baseOffset + instructions.size();
    final int linesBefore = instructions.size();
    final OperandSize sourceSize = sourceResult.getSize();
    final OperandSize targetSize = targetResult.getSize();
    final String sourceRegister = sourceResult.getRegister();
    final String targetRegister = targetResult.getRegister();
    final String rotateMask = environment.getNextVariableString();
    final String rotateMaskZero = environment.getNextVariableString();
    final String rotateMaskLessOne = environment.getNextVariableString();
    final String rotateMaskOne = environment.getNextVariableString();
    final String shrValue = environment.getNextVariableString();
    final String shredResult = environment.getNextVariableString();
    final String shlValue = environment.getNextVariableString();
    final String shledResult = environment.getNextVariableString();
    final String result = environment.getNextVariableString();
    final String tempCf = environment.getNextVariableString();
    final String tempOf = environment.getNextVariableString();
    final String tempOfLsb = environment.getNextVariableString();
    final String msbMask = String.valueOf(TranslationHelpers.getMsbMask(targetSize));
    final String modVal = String.valueOf(targetSize.getBitSize());
    final String msbMask2nd = String.valueOf(TranslationHelpers.getMsbMask(targetSize) / 2);
    final String shiftMsbLsb = String.valueOf(TranslationHelpers.getShiftMsbLsbMask(targetSize));
    final String shift2ndMsbLsb = String.valueOf(TranslationHelpers.getShiftMsbLsbMask(targetSize) + 1);
    // Make sure to rotate less than the size of the register
    instructions.add(ReilHelpers.createMod(offset, sourceSize, sourceRegister, targetSize, modVal, targetSize, rotateMask));
    // Find out if the rotate mask is 0 and negate the result
    instructions.add(ReilHelpers.createBisz(offset + 1, targetSize, rotateMask, OperandSize.BYTE, rotateMaskZero));
    // Find out if the rotate mask is 1
    instructions.add(ReilHelpers.createSub(offset + 2, targetSize, rotateMask, targetSize, "1", targetSize, rotateMaskLessOne));
    instructions.add(ReilHelpers.createBisz(offset + 3, targetSize, rotateMaskLessOne, OperandSize.BYTE, rotateMaskOne));
    // Negate the rotate-mask => ROT to the right
    instructions.add(ReilHelpers.createSub(offset + 4, OperandSize.BYTE, "0", OperandSize.BYTE, rotateMask, OperandSize.BYTE, shrValue));
    // Perform the rotate
    instructions.add(ReilHelpers.createBsh(offset + 5, targetSize, targetRegister, OperandSize.BYTE, shrValue, targetSize, shredResult));
    instructions.add(ReilHelpers.createSub(offset + 6, OperandSize.BYTE, modVal, OperandSize.BYTE, rotateMask, OperandSize.BYTE, shlValue));
    instructions.add(ReilHelpers.createBsh(offset + 7, targetSize, targetRegister, OperandSize.BYTE, shlValue, targetSize, shledResult));
    instructions.add(ReilHelpers.createOr(offset + 8, targetSize, shredResult, targetSize, shledResult, targetSize, result));
    // Don't change the flags if the rotate value was zero
    final String jmpGoal = String.format("%d.%d", instruction.getAddress().toLong(), linesBefore + 18);
    instructions.add(ReilHelpers.createJcc(offset + 9, OperandSize.BYTE, rotateMaskZero, OperandSize.ADDRESS, jmpGoal));
    // Set the CF to the new MSB
    instructions.add(ReilHelpers.createAnd(offset + 10, targetSize, result, targetSize, msbMask, targetSize, tempCf));
    instructions.add(ReilHelpers.createBsh(offset + 11, targetSize, tempCf, targetSize, shiftMsbLsb, OperandSize.BYTE, Helpers.CARRY_FLAG));
    // The OF needs to be set to a different value if the rotate-mask was 1
    final String jmpGoal2 = String.format("%d.%d", instruction.getAddress().toLong(), linesBefore + 15);
    instructions.add(ReilHelpers.createJcc(offset + 12, OperandSize.BYTE, rotateMaskOne, OperandSize.ADDRESS, jmpGoal2));
    // Set the OF to undefined if the rotate-mask was positive but not 1
    instructions.add(ReilHelpers.createUndef(offset + 13, OperandSize.BYTE, Helpers.OVERFLOW_FLAG));
    // Jump to the end
    final String jmpGoal3 = String.format("%d.%d", instruction.getAddress().toLong(), linesBefore + 18);
    instructions.add(ReilHelpers.createJcc(offset + 14, OperandSize.BYTE, "1", OperandSize.ADDRESS, jmpGoal3));
    // Set the OF to the old MSB
    instructions.add(ReilHelpers.createAnd(offset + 15, targetSize, result, targetSize, msbMask2nd, targetSize, tempOf));
    instructions.add(ReilHelpers.createBsh(offset + 16, targetSize, tempOf, targetSize, shift2ndMsbLsb, OperandSize.BYTE, tempOfLsb));
    instructions.add(ReilHelpers.createXor(offset + 17, OperandSize.BYTE, tempOfLsb, OperandSize.BYTE, Helpers.CARRY_FLAG, OperandSize.BYTE, Helpers.OVERFLOW_FLAG));
    Helpers.writeBack(environment, offset + 18, targetOperand, result, targetResult.getSize(), targetResult.getAddress(), targetResult.getType(), instructions);
}
Also used : IOperandTree(com.google.security.zynamics.zylib.disassembly.IOperandTree) InternalTranslationException(com.google.security.zynamics.reil.translators.InternalTranslationException) TranslationResult(com.google.security.zynamics.reil.translators.TranslationResult) OperandSize(com.google.security.zynamics.reil.OperandSize)

Example 34 with InternalTranslationException

use of com.google.security.zynamics.reil.translators.InternalTranslationException in project binnavi by google.

the class SahfTranslator method translate.

/**
   * Translates a SAHF instruction to REIL code.
   * 
   * @param environment A valid translation environment.
   * @param instruction The SAHF instruction to translate.
   * @param instructions The generated REIL code will be added to this list
   * 
   * @throws InternalTranslationException if any of the arguments are null the passed instruction is
   *         not an SAHF instruction
   */
@Override
public void translate(final ITranslationEnvironment environment, final IInstruction instruction, final List<ReilInstruction> instructions) throws InternalTranslationException {
    TranslationHelpers.checkTranslationArguments(environment, instruction, instructions, "sahf");
    if (instruction.getOperands().size() != 0) {
        throw new InternalTranslationException("Error: Argument instruction is not a sahf instruction (invalid number of operands)");
    }
    final long baseOffset = instruction.getAddress().toLong() * 0x100;
    final OperandSize archSize = environment.getArchitectureSize();
    final String shiftedEaxToCf = environment.getNextVariableString();
    final String shiftedEaxToPf = environment.getNextVariableString();
    final String shiftedEaxToAf = environment.getNextVariableString();
    final String shiftedEaxToZf = environment.getNextVariableString();
    final String shiftedEaxToSf = environment.getNextVariableString();
    // Shift the future CF into the lowest byte and put it into the CF
    instructions.add(ReilHelpers.createBsh(baseOffset, archSize, "eax", archSize, "-8", archSize, shiftedEaxToCf));
    instructions.add(ReilHelpers.createAnd(baseOffset + 1, archSize, shiftedEaxToCf, archSize, "1", OperandSize.BYTE, Helpers.CARRY_FLAG));
    // Shift the future PF into the lowest byte and put it into the PF
    instructions.add(ReilHelpers.createBsh(baseOffset + 2, archSize, "eax", archSize, "-10", archSize, shiftedEaxToPf));
    instructions.add(ReilHelpers.createAnd(baseOffset + 3, archSize, shiftedEaxToPf, archSize, "1", OperandSize.BYTE, Helpers.PARITY_FLAG));
    // Shift the future AF into the lowest byte and put it into the AF
    instructions.add(ReilHelpers.createBsh(baseOffset + 4, archSize, "eax", archSize, "-12", archSize, shiftedEaxToAf));
    instructions.add(ReilHelpers.createAnd(baseOffset + 5, archSize, shiftedEaxToAf, archSize, "1", OperandSize.BYTE, Helpers.AUXILIARY_FLAG));
    // Shift the future ZF into the lowest byte and put it into the ZF
    instructions.add(ReilHelpers.createBsh(baseOffset + 6, archSize, "eax", archSize, "-14", archSize, shiftedEaxToZf));
    instructions.add(ReilHelpers.createAnd(baseOffset + 7, archSize, shiftedEaxToZf, archSize, "1", OperandSize.BYTE, Helpers.ZERO_FLAG));
    // Shift the future SF into the lowest byte and put it into the SF
    instructions.add(ReilHelpers.createBsh(baseOffset + 8, archSize, "eax", archSize, "-15", archSize, shiftedEaxToSf));
    instructions.add(ReilHelpers.createAnd(baseOffset + 9, archSize, shiftedEaxToSf, archSize, "1", OperandSize.BYTE, Helpers.SIGN_FLAG));
}
Also used : InternalTranslationException(com.google.security.zynamics.reil.translators.InternalTranslationException) OperandSize(com.google.security.zynamics.reil.OperandSize)

Example 35 with InternalTranslationException

use of com.google.security.zynamics.reil.translators.InternalTranslationException in project binnavi by google.

the class SbbTranslator method translate.

/**
   * Translates a SBB instruction to REIL code.
   *
   * @param environment A valid translation environment.
   * @param instruction The SBB instruction to translate.
   * @param instructions The generated REIL code will be added to this list
   *
   * @throws InternalTranslationException if any of the arguments are null the passed instruction is
   *         not an SBB instruction
   */
@Override
public void translate(final ITranslationEnvironment environment, final IInstruction instruction, final List<ReilInstruction> instructions) throws InternalTranslationException {
    TranslationHelpers.checkTranslationArguments(environment, instruction, instructions, "sbb");
    if (instruction.getOperands().size() != 2) {
        throw new InternalTranslationException("Error: Argument instruction is not a sbb instruction (invalid number of operand)");
    }
    final long baseOffset = instruction.getAddress().toLong() * 0x100;
    long offset = baseOffset;
    final List<? extends IOperandTree> operands = instruction.getOperands();
    final IOperandTree targetOperand = operands.get(0);
    final IOperandTree sourceOperand = operands.get(1);
    // Load source operand.
    final TranslationResult sourceResult = Helpers.translateOperand(environment, offset, sourceOperand, true);
    instructions.addAll(sourceResult.getInstructions());
    // Adjust the offset of the next REIL instruction.
    offset = baseOffset + instructions.size();
    // Load target operand.
    final TranslationResult targetResult = Helpers.translateOperand(environment, offset, targetOperand, true);
    instructions.addAll(targetResult.getInstructions());
    // Adjust the offset of the next REIL instruction.
    offset = baseOffset + instructions.size();
    if (sourceResult.getSize() != targetResult.getSize()) {
        throw new InternalTranslationException("Error: The operands of SBB instructions must have equal size");
    }
    final OperandSize size = sourceResult.getSize();
    final String sourceRegister = sourceResult.getRegister();
    final String targetRegister = targetResult.getRegister();
    final String msbMask = String.valueOf(TranslationHelpers.getMsbMask(size));
    final String carryMask = String.valueOf(Helpers.getCarryMask(size));
    final String truncateMask = String.valueOf(TranslationHelpers.getAllBitsMask(size));
    final String shiftValue = String.valueOf(TranslationHelpers.getShiftMsbLsbMask(size));
    final String shiftCarry = String.valueOf(-size.getBitSize());
    final OperandSize resultSize = TranslationHelpers.getNextSize(size);
    final String msb1 = environment.getNextVariableString();
    final String msb2 = environment.getNextVariableString();
    final String subResult = environment.getNextVariableString();
    final String subResultTemp = environment.getNextVariableString();
    final String msbResult = environment.getNextVariableString();
    final String msbSameBefore = environment.getNextVariableString();
    final String msbChanged = environment.getNextVariableString();
    final String tempOf = environment.getNextVariableString();
    final String tempCf = environment.getNextVariableString();
    final String truncatedResult = environment.getNextVariableString();
    // Isolate the MSBs of the two operands
    instructions.add(ReilHelpers.createAnd(offset, size, sourceRegister, size, msbMask, size, msb1));
    instructions.add(ReilHelpers.createAnd(offset + 1, size, targetRegister, size, msbMask, size, msb2));
    // Perform the subtraction
    instructions.add(ReilHelpers.createSub(offset + 2, size, sourceRegister, size, targetRegister, resultSize, subResultTemp));
    instructions.add(ReilHelpers.createSub(offset + 3, resultSize, subResultTemp, OperandSize.BYTE, Helpers.CARRY_FLAG, resultSize, subResult));
    // Isolate the MSB of the result and put it into the Sign Flag
    instructions.add(ReilHelpers.createAnd(offset + 4, resultSize, subResult, resultSize, msbMask, size, msbResult));
    instructions.add(ReilHelpers.createBsh(offset + 5, size, msbResult, size, shiftValue, OperandSize.BYTE, Helpers.SIGN_FLAG));
    // Find out if the MSB of the two operands were different and whether the MSB of the first
    // operand changed
    instructions.add(ReilHelpers.createXor(offset + 6, size, msb1, size, msb2, size, msbSameBefore));
    instructions.add(ReilHelpers.createXor(offset + 7, size, msb1, size, msbResult, size, msbChanged));
    instructions.add(ReilHelpers.createAnd(offset + 8, size, msbSameBefore, size, msbChanged, size, tempOf));
    // Write the result into the Overflow Flag
    instructions.add(ReilHelpers.createBsh(offset + 9, size, tempOf, size, shiftValue, OperandSize.BYTE, Helpers.OVERFLOW_FLAG));
    // Update the Carry Flag
    instructions.add(ReilHelpers.createAnd(offset + 10, resultSize, subResult, resultSize, carryMask, resultSize, tempCf));
    instructions.add(ReilHelpers.createBsh(offset + 11, resultSize, tempCf, resultSize, shiftCarry, OperandSize.BYTE, Helpers.CARRY_FLAG));
    // Truncate the result to fit into the target
    instructions.add(ReilHelpers.createAnd(offset + 12, resultSize, subResult, resultSize, truncateMask, size, truncatedResult));
    // Update the Zero Flag
    instructions.add(ReilHelpers.createBisz(offset + 13, size, truncatedResult, OperandSize.BYTE, Helpers.ZERO_FLAG));
    // Write the result of the subtraction back to the target register
    Helpers.writeBack(environment, offset + 14, targetOperand, truncatedResult, size, targetResult.getAddress(), targetResult.getType(), instructions);
}
Also used : IOperandTree(com.google.security.zynamics.zylib.disassembly.IOperandTree) InternalTranslationException(com.google.security.zynamics.reil.translators.InternalTranslationException) TranslationResult(com.google.security.zynamics.reil.translators.TranslationResult) OperandSize(com.google.security.zynamics.reil.OperandSize)

Aggregations

InternalTranslationException (com.google.security.zynamics.reil.translators.InternalTranslationException)62 OperandSize (com.google.security.zynamics.reil.OperandSize)46 TranslationResult (com.google.security.zynamics.reil.translators.TranslationResult)42 IOperandTree (com.google.security.zynamics.zylib.disassembly.IOperandTree)35 ReilInstruction (com.google.security.zynamics.reil.ReilInstruction)6 ArrayList (java.util.ArrayList)5 TranslationResultType (com.google.security.zynamics.reil.translators.TranslationResultType)3 INaviInstruction (com.google.security.zynamics.binnavi.disassembly.INaviInstruction)2 OperandType (com.google.security.zynamics.reil.OperandType)2 IOperandTreeNode (com.google.security.zynamics.zylib.disassembly.IOperandTreeNode)2 BigInteger (java.math.BigInteger)2 MockCodeNodeData (com.google.security.zynamics.binnavi.Database.MockClasses.MockCodeNodeData)1 MockCodeNodeProvider (com.google.security.zynamics.binnavi.Database.MockClasses.MockCodeNodeProvider)1 MockSqlProvider (com.google.security.zynamics.binnavi.Database.MockClasses.MockSqlProvider)1 CCodeNodeParser (com.google.security.zynamics.binnavi.Database.NodeParser.CCodeNodeParser)1 MaybeNullException (com.google.security.zynamics.binnavi.Exceptions.MaybeNullException)1 CCodeNode (com.google.security.zynamics.binnavi.disassembly.CCodeNode)1 INaviCodeNode (com.google.security.zynamics.binnavi.disassembly.INaviCodeNode)1 MockFunction (com.google.security.zynamics.binnavi.disassembly.MockFunction)1 MockModule (com.google.security.zynamics.binnavi.disassembly.Modules.MockModule)1