Ejemplo n.º 1
0
 def analyseGadgets(self, fileObject):
     gadgets = fileObject.gadgets
     analyser = Analyser()
     cb = None
     lg = len(gadgets)
     if self.__callbacks and hasattr(self.__callbacks, '__analyseGadgetsProgress__'):
         cb = self.__callbacks.__analyseGadgetsProgress__
     for i,g in enumerate(gadgets):
         g.info = analyser.analyse(g)
         if cb:
             cb(g, float(i)/lg)
     if cb:
          cb(None, 1.0)
     self.__saveCache(fileObject)
     fileObject.analysed = True
Ejemplo n.º 2
0
 def analyseGadgets(self, fileObject):
     gadgets = fileObject.gadgets
     analyser = Analyser()
     cb = None
     lg = len(gadgets)
     if self.__callbacks and hasattr(self.__callbacks, '__analyseGadgetsProgress__'):
         cb = self.__callbacks.__analyseGadgetsProgress__
     for i,g in enumerate(gadgets):
         g.info = analyser.analyse(g)
         if cb:
             cb(g, float(i)/lg)
     if cb:
          cb(None, 1.0)
     self.__saveCache(fileObject)
     fileObject.analysed = True
Ejemplo n.º 3
0
class Gadget(object):

    DETAILED = False
    IMAGE_BASES = {}
    ANALYSER = Analyser()

    def __init__(self, fileName, section, arch, lines=None, bytes=None, semantic_information=None):
        #super(Gadget, self).__init__()
        if isinstance(arch, str):
            arch = ropper.arch.getArchitecture(arch)
        self.__arch = arch
        self.__lines = lines
        self.__gadget = None
        self.__category = None
        self._fileName = fileName
        self._section = section
        self.__bytes = bytes
        self.__info = semantic_information
        self.__analysed = semantic_information is not None
        #if init:
        #    self.__initialize(lines, bytes)

    @property
    def info(self):
        
        return self.__info

    @info.setter
    def info(self, info):
        self.__info = info

    @property
    def arch(self):
        return self.__arch
    
    @property
    def lines(self):
        if self.__lines == None:
            self.__lines = []
        return self.__lines

    @property
    def _lines(self):
        if self.__lines == None:
            self.__lines = []
        return self.__lines

    @_lines.setter
    def _lines(self, value):
        self.__lines = value

    @property
    def section(self):
        return self._section

    @property
    def fileName(self):
        return self._fileName

    @property
    def _bytes(self):
        if self.__bytes == None:
            self.__bytes = bytearray()
        return self.__bytes

    @_bytes.setter
    def _bytes(self, value):
        self.__bytes = value


    @property
    def bytes(self):
        if self.__bytes == None:
            self.__bytes = bytearray()
        return self.__bytes

    @bytes.setter
    def bytes(self, bytes):
        self.__bytes = bytes

    @property
    def imageBase(self):
        return Gadget.IMAGE_BASES.get(self._fileName,0)

    @property
    def address(self):
        return self.imageBase + self.lines[0][0]

    @property
    def _gadget(self):
        if not self.__gadget:
            self.__gadget = ''
            for line in self.lines:
                self.__gadget += line[1] + '; '
        return self.__gadget

    @_gadget.setter
    def _gadget(self, value):
        self.__gadget = value

    def __initialize(self, lines, bytes):
        if bytes:
            self._bytes = bytes
        self.__lines = lines

    def append(self, address, mnem, args='', bytes=None):
        if args:
            self._lines.append((address, mnem + ' ' + args, mnem ,args))
            self._gadget += mnem + ' ' + args + '; '
        else:
            self._lines.append((address, mnem, mnem,args))
            self._gadget += mnem + '; '

        if bytes:
            self.bytes += bytes

    def match(self, filter):
        if not filter or len(filter) == 0:
            return True
        if self.__arch in (ropper.arch.ARMTHUMB, ropper.arch.ARM):
            return bool(re.match(filter, self._gadget.replace('.w','')))
        else:
            return bool(re.match(filter, self._gadget))

    def addressesContainsBytes(self, badbytes):
        line =  self._lines[0]
        for b in badbytes:

            address = self.address
            if type(b) == str:
                b = ord(b)

            # TODO: This should be changed. Only 4 bytes are checked
            for i in range(self.arch.addressLength):
                if (address & 0xff) == b:

                    return True
                address >>= 8

    def simpleInstructionString(self):
        toReturn = ''
        for line in self._lines:
            if line[3]:
                toReturn += cstr(line[2], Color.LIGHT_YELLOW)+ ' ' + cstr(line[3], Color.LIGHT_GRAY)+ cstr('; ', Color.LIGHT_BLUE)
            else:
                toReturn += cstr(line[2], Color.LIGHT_YELLOW)+ cstr('; ', Color.LIGHT_BLUE)


        return toReturn

    def simpleString(self):
        analyseColor = Color.CYAN if self.__info else Color.RED
        address = self.__lines[0][0]
        
        if isinstance(self.arch, ropper.arch.ArchitectureArmThumb):
            address += 1
            toReturn = '%s (%s): ' % (cstr(toHex(self._lines[0][0] + self.imageBase, self.__arch.addressLength), analyseColor),cstr(toHex(address + self.imageBase, self.__arch.addressLength), Color.GREEN))
        else:
            toReturn = '%s: ' % cstr(toHex(self._lines[0][0] + self.imageBase, self.__arch.addressLength), analyseColor)
        toReturn += self.simpleInstructionString()
        if self.__info:
            toReturn += '\nClobbered Register = %s; StackPointer-Offset = %s\n' % (", ".join(list(self.info.clobberedRegisters)),self.info.spOffset if self.info.spOffset is not None else 'Undef')
        return toReturn

    @property
    def category(self):
        if not self.__category:
            line = self.__lines[0][1]
            for cat, regexs in self.__arch._categories.items():
                for regex in regexs[0]:
                    match = re.match(regex, line)
                    if match:
                        for invalid in regexs[1]:
                            for l in self.__lines[1:]:
                                if l[1].startswith(invalid):
                                    self.__category = (Category.NONE,)
                                    return self.__category
                        d = match.groupdict()
                        for key, value in d.items():
                            d[key] = str(value)

                        self.__category = (cat, len(self.__lines) -1 ,match.groupdict())
                        return self.__category
            self.__category = (Category.NONE,)

        return self.__category

    def __len__(self):
        return len(self._lines)

    def __cmp__(self, other):
        if isinstance(other, self.__class__) and len(self) == len(other):
            return cmp(str(self),str(other))
        return -1

    def disassemblyString(self):
        toReturn = ''
        for line in self._lines:
            toReturn += cstr(toHex(line[0] + self.imageBase, self.__arch.addressLength), Color.RED) +': '+ cstr(line[1], Color.LIGHT_GRAY) + '\n'

        return toReturn

    def __str__(self):
        if not Gadget.DETAILED:
            return self.simpleString()
        if not len(self._lines):
            return "empty gadget"
        address = self._lines[0][0]
        if self.__arch == ropper.arch.ARMTHUMB:
            address += 1
            toReturn = cstr('Gadget', Color.BLUE)+': %s (%s)\n' % (cstr(toHex(self._lines[0][0] + self.imageBase, self.__arch.addressLength), Color.YELLOW),cstr(toHex(address+ self.imageBase, self.__arch.addressLength), Color.GREEN))
        else:
            toReturn = cstr('Gadget', Color.BLUE)+': %s\n' % (cstr(toHex(self._lines[0][0] + self.imageBase, self.__arch.addressLength), Color.YELLOW))
        for line in self._lines:
            toReturn += cstr(toHex(line[0] + self.imageBase, self.__arch.addressLength), Color.RED) +': '+ cstr(line[1], Color.LIGHT_GRAY) + '\n'

        return toReturn

    def __repr__(self):
        return 'Gadget(%s, %s, %s, %s, %s, %s)' % (repr(self.fileName), repr(self.section), repr(self.__arch), repr(self.__lines), repr(self._bytes), repr(self.info))
Ejemplo n.º 4
0
RESULTS_DIR = 'results/'
NUCLEUS = '../nucleus/nucleus'
RESULTS_SUBDIR_PATTERN = 'results/{}/'
OUTFILE_PATTERN = 'results/{}/{}-g{}_{}.json'

options = {
    'color': False,
    'badbytes': '00',
    'all': True,
    'inst_count': 6,
    'type': 'rop',
    'detailed': False
}

rs = RopperService(options)
analyser = Analyser()


def ropper_analyser(gadget):
    try:
        arch = ArchitectureX86()
        irsb = pyvex.IRSB(bytes(gadget['bytes']),
                          gadget['vaddr'],
                          arch.info,
                          bytes_offset=0,
                          num_bytes=len(gadget['bytes']),
                          opt_level=0)
        irsb_anal = IRSBAnalyser()
        anal = irsb_anal.analyse(irsb)
        archinfo = arch.info
        anal.spOffset = analyser.findSpOffset(