Ejemplo n.º 1
0
 version = int(arch.split("_")[1])
 with open(sys.argv[1]) as f:
     for line in f:
         pos = []
         count += 1
         if count == limit:
             break
         line_split = line.split()
         # Construct instruction structure
         origin = Inst(line_split)
         # Find the 64-bit encodings
         base = int(origin.enc(), 16)
         origin_operand_types = check_operand_types(origin)
         if len(origin.operands()) and origin_operand_types.find('X') == -1:
             pp = [[] for i in range(len(origin_operand_types))]
             logging.info(origin.op() + " " + origin.modifier())
             logging.info("0b{:064b}".format(base) + ": " +
                          origin.operands())
             for i in range(0, 64):
                 mask = 2**i
                 newcode = base ^ mask
                 # Disassemble the new code
                 dump_file = dump("0x{:016x}".format(newcode), arch)
                 if dump_file and dump_file.find(
                         "?") == -1 and dump_file.find("error") == -1:
                     line = dump_file.split("\n")
                     if version < 40:
                         line_inst = line[1].split()
                     else:
                         line_inst = line[5].split()
                     # [0]: header info, [1] instruction part
Ejemplo n.º 2
0
                # Disassemble the new code
                dump_file = dump("0x{:016x}".format(newcode), arch)
                # Compare the disassemble to check which field changes: opcode, operand or modifer
                if dump_file and dump_file.find("?") == -1 and dump_file.find(
                        "error") == -1:
                    line = dump_file.split("\n")
                    if version < 40:
                        line_inst = line[1].split()
                    else:
                        line_inst = line[5].split()
                    # [0]: header info, [1] instruction part
                    line_inst.pop(0)
                    # Parse the new generated disassembly
                    inst = Inst(line_inst, raw=version > 40)
                    # If opcode is changed, then this bit represent opcode, we find it!
                    # LDG and TEX are the same instructions in fact
                    # RED and ATOM are the same instruction
                    if inst.op() != origin.op() and not i in pos and not \
                    (inst.op() == "LDG" and origin.op() == "TEX") and not \
                    (inst.op() == "TEX" and origin.op() =="LDG") and not \
                    (inst.op() == "RED" and origin.op() == "ATOM") and not \
                    (inst.op() == "ATOM" and origin.op() == "RED"):
                        logging.info("Opcode changes: %s => %s when bit [%d] is flipped from [%d]", \
                            origin.op(), inst.op(), i, (base >> i) & 0x1)
                        bits = bits | (((base >> i) & 0x1) << i)
                        pos.append(i)
            if len(pos) > 0:
                logging.info(
                    "0b{:064b}".format(bits) + ": %s opcode bits %s: ",
                    origin.op(), pos)
Ejemplo n.º 3
0
from sets import Set
from inst import Inst
import subprocess
import sys

if __name__ == "__main__":
    opset = Set([])
    with open(sys.argv[1]) as f:
        for line in f:
            field = line.split()
            inst = Inst(field, False)
            if not inst.op() in opset:
                opset.add(inst.op())
                sys.stdout.write(line)
Ejemplo n.º 4
0
            # Construct instruction structure
            origin = Inst(line_split)
            # Find the 64-bit encodings
            base = int(origin.enc(), 16)
            # Bit by bit xor, observe whether opcode changes and guess what this bit represent
            for i in range(0, 64):
                mask = 2**i
                newcode = base ^ mask
                # Disassemble the new code
                dump_file = dump("0x{:016x}".format(newcode), arch)
                # Compare the disassemble to check which field changes: opcode, operand or modifer
                if dump_file and dump_file.find("?") == -1 and dump_file.find(
                        "error") == -1:
                    line = dump_file.split("\n")
                    if version < 40:
                        line_inst = line[1].split()
                    else:
                        line_inst = line[5].split()
                    # [0]: header info, [1] instruction part
                    line_inst.pop(0)
                    # Parse the new generated disassembly
                    inst = Inst(line_inst, raw=version > 40)
                    if inst.modifier() != origin.modifier() and inst.op(
                    ) == origin.op():
                        if i not in pos:
                            pos.append(i)
            # Enumerate all modifiers
            if len(pos) > 0:
                logging.info("%s modifier bits %s: ", origin.op(), pos)
                enumerator.enumerate(base, pos, arch)