コード例 #1
0
ファイル: strncpy.py プロジェクト: zhuyue1314/simuvex
    def run(self, dst_addr, src_addr, limit, src_len=None):
        self.argument_types = {
            0: self.ty_ptr(SimTypeString()),
            1: self.ty_ptr(SimTypeString()),
            2: SimTypeLength(self.state.arch)
        }
        self.return_type = self.ty_ptr(SimTypeString())

        strlen = simuvex.SimProcedures['libc.so.6']['strlen']
        memcpy = simuvex.SimProcedures['libc.so.6']['memcpy']

        src_len = src_len if src_len is not None else self.inline_call(
            strlen, src_addr)
        cpy_size = self.state.se.If(
            self.state.se.ULE(limit, src_len.ret_expr + 1), limit,
            src_len.ret_expr + 1)

        #print "==================="
        #print sorted(self.state.expr_value(src_len.ret_expr).se.any_n(20))
        #print self.state.expr_value(limit.expr).se.any_n(20)
        #print sorted(self.state.expr_value(cpy_size).se.any_n(20))
        #print "-------------------"

        self.inline_call(memcpy, dst_addr, src_addr, cpy_size)
        return dst_addr
コード例 #2
0
    def run(self, scan, fmt):

        #additional code
        trace_data = ("__isoc99_sscanf", {
            "scan": (scan, scan.symbolic),
            "fmt": (fmt, fmt.symbolic)
        })
        try:
            self.state.procedure_data.global_variables["trace"].append(
                trace_data)
        except KeyError:
            self.state.procedure_data.global_variables["trace"] = []
            self.state.procedure_data.global_variables["trace"].append(
                trace_data)
        #end of additional code

        #pylint:disable=attribute-defined-outside-init

        self.argument_types = {
            0: self.ty_ptr(SimTypeString()),
            1: self.ty_ptr(SimTypeString())
        }
        self.return_type = SimTypeInt(self.state.arch.bits, True)

        fmt_str = self._parse(1)

        _, items = fmt_str.interpret(self.arg(0),
                                     2,
                                     self.arg,
                                     region=self.state.memory)

        return items
コード例 #3
0
    def run(self, dst, src):

        #additional code
        trace_data = ("strcpy", {
            "dst": (dst, dst.symbolic),
            "src": (src, src.symbolic)
        })
        try:
            self.state.procedure_data.global_variables["trace"].append(
                trace_data)
        except KeyError:
            self.state.procedure_data.global_variables["trace"] = []
            self.state.procedure_data.global_variables["trace"].append(
                trace_data)
        #end of additional code

        self.argument_types = {
            0: self.ty_ptr(SimTypeString()),
            1: self.ty_ptr(SimTypeString())
        }
        self.return_type = self.ty_ptr(SimTypeString())

        strlen = simuvex.SimProcedures['libc.so.6']['strlen']
        strncpy = simuvex.SimProcedures['libc.so.6']['strncpy']
        src_len = self.inline_call(strlen, src)

        ret_expr = self.inline_call(strncpy,
                                    dst,
                                    src,
                                    src_len.ret_expr + 1,
                                    src_len=src_len.ret_expr).ret_expr
        return ret_expr
コード例 #4
0
ファイル: strstr.py プロジェクト: zhuyue1314/simuvex
    def run(self, haystack_addr, needle_addr, haystack_strlen=None, needle_strlen=None):
        self.argument_types = { 0: self.ty_ptr(SimTypeString()),
                                1: self.ty_ptr(SimTypeString())}
        self.return_type = self.ty_ptr(SimTypeString())

        strlen = simuvex.SimProcedures['libc.so.6']['strlen']
        strncmp = simuvex.SimProcedures['libc.so.6']['strncmp']

        haystack_strlen = self.inline_call(strlen, haystack_addr) if haystack_strlen is None else haystack_strlen
        needle_strlen = self.inline_call(strlen, needle_addr) if needle_strlen is None else needle_strlen

        # naive approach
        haystack_maxlen = haystack_strlen.max_null_index
        needle_maxlen = needle_strlen.max_null_index

        l.debug("strstr with size %d haystack and size %d needle...", haystack_maxlen, needle_maxlen)

        if needle_maxlen == 0:
            l.debug("... zero-length needle.")
            return haystack_addr
        elif haystack_maxlen == 0:
            l.debug("... zero-length haystack.")
            return self.state.se.BitVecVal(0, self.state.arch.bits)

        if self.state.se.symbolic(needle_strlen.ret_expr):
            cases = [ [ needle_strlen.ret_expr == 0, haystack_addr ] ]
            exclusions = [ needle_strlen.ret_expr != 0 ]
            remaining_symbolic = self.state.libc.max_symbolic_strstr
            for i in range(haystack_maxlen):
                l.debug("... case %d (%d symbolic checks remaining)", i, remaining_symbolic)

                # big hack!
                cmp_res = self.inline_call(strncmp, haystack_addr + i, needle_addr, needle_strlen.ret_expr, a_len=haystack_strlen, b_len=needle_strlen)
                c = self.state.se.And(*([ self.state.se.UGE(haystack_strlen.ret_expr, needle_strlen.ret_expr), cmp_res.ret_expr == 0 ] + exclusions))
                exclusions.append(cmp_res.ret_expr != 0)

                if self.state.se.symbolic(c):
                    remaining_symbolic -= 1

                #print "CASE:", c
                cases.append([ c, haystack_addr + i ])
                haystack_strlen.ret_expr = haystack_strlen.ret_expr - 1

                if remaining_symbolic == 0:
                    l.debug("... exhausted remaining symbolic checks.")
                    break

            cases.append([ self.state.se.And(*exclusions), self.state.se.BVV(0, self.state.arch.bits) ])
            l.debug("... created %d cases", len(cases))
            r = self.state.se.ite_cases(cases, 0)
            c = [ self.state.se.Or(*[c for c,_ in cases]) ]
        else:
            needle_length = self.state.se.any_int(needle_strlen.ret_expr)
            needle_str = self.state.memory.load(needle_addr, needle_length)

            r, c, i = self.state.memory.find(haystack_addr, needle_str, haystack_strlen.max_null_index, max_symbolic_bytes=self.state.libc.max_symbolic_strstr, default=0)

        self.state.add_constraints(*c)
        return r
コード例 #5
0
    def run(self, dst, src):
        self.argument_types = {0: self.ty_ptr(SimTypeString()),
                               1: self.ty_ptr(SimTypeString())}
        self.return_type = self.ty_ptr(SimTypeString())

        strlen = simuvex.SimProcedures['libc.so.6']['strlen']
        strncpy = simuvex.SimProcedures['libc.so.6']['strncpy']
        src_len = self.inline_call(strlen, src)

        ret_expr = self.inline_call(strncpy, dst, src, src_len.ret_expr+1, src_len=src_len.ret_expr).ret_expr
        return ret_expr
コード例 #6
0
ファイル: __isoc99_sscanf.py プロジェクト: themaks/simuvex
    def run(self, scan, fmt):
        #pylint:disable=attribute-defined-outside-init

        self.argument_types = {0: self.ty_ptr(SimTypeString()),
                               1: self.ty_ptr(SimTypeString())}
        self.return_type = SimTypeInt(self.state.arch.bits, True)

        fmt_str = self._parse(1)

        _, items = fmt_str.interpret(self.arg(0), 2, self.arg, region=self.state.memory)

        return items
コード例 #7
0
ファイル: strcasecmp.py プロジェクト: themaks/simuvex
    def run(self, a_addr, b_addr):
        self.argument_types = { 0: self.ty_ptr(SimTypeString()),
                                   1: self.ty_ptr(SimTypeString())}
        self.return_type = SimTypeInt(32, True)

        strlen = simuvex.SimProcedures['libc.so.6']['strlen']

        a_strlen = self.inline_call(strlen, a_addr)
        b_strlen = self.inline_call(strlen, b_addr)
        maxlen = self.state.se.BVV(max(a_strlen.max_null_index, b_strlen.max_null_index), self.state.arch.bits)

        strncmp = self.inline_call(simuvex.SimProcedures['libc.so.6']['strncmp'], a_addr, b_addr, maxlen, a_len=a_strlen, b_len=b_strlen)
        return strncmp.ret_expr
コード例 #8
0
ファイル: strdup.py プロジェクト: stef/simuvex
    def run(self, s):
        self.argument_types = {0: self.ty_ptr(SimTypeString())}
        self.return_type = self.ty_ptr(SimTypeString())

        strlen = simuvex.SimProcedures['libc.so.6']['strlen']
        strncpy = simuvex.SimProcedures['libc.so.6']['strncpy']
        malloc = simuvex.SimProcedures['libc.so.6']['malloc']

        src_len = self.inline_call(strlen, s).ret_expr
        new_s = self.inline_call(malloc, src_len + 1).ret_expr

        self.inline_call(strncpy, new_s, s, src_len + 1, src_len=src_len)

        return new_s
コード例 #9
0
    def run(self, fmt):

        #additional code
        trace_data = ("__isoc99_scanf", {"fmt": (fmt, fmt.symbolic)})
        try:
            self.state.procedure_data.global_variables["trace"].append(trace_data)
        except KeyError:
            self.state.procedure_data.global_variables["trace"] = []
            self.state.procedure_data.global_variables["trace"].append(trace_data)
        #end of additional code

        #pylint:disable=attribute-defined-outside-init

        self.argument_types = {0: self.ty_ptr(SimTypeString())}
        self.return_type = SimTypeInt(self.state.arch.bits, True)

        fmt_str = self._parse(0)

        # we're reading from stdin so the region is the file's content
        f = self.state.posix.get_file(0)
        region = f.content
        start = f.pos

        (end, items) = fmt_str.interpret(start, 1, self.arg, region=region)

        # do the read, correcting the internal file position and logging the action
        self.state.posix.read_from(0, end - start)

        return items
コード例 #10
0
ファイル: strchr.py プロジェクト: themaks/simuvex
    def run(self, s_addr, c_int, s_strlen=None):
        c = c_int[7:0]

        self.argument_types = {
            0: self.ty_ptr(SimTypeString()),
            1: SimTypeInt(32, True)
        }  # ?
        self.return_type = self.ty_ptr(SimTypeChar())  # ?

        s_strlen = self.inline_call(
            simuvex.SimProcedures['libc.so.6']['strlen'], s_addr)

        if self.state.se.symbolic(s_strlen.ret_expr):
            l.debug("symbolic strlen")
            # TODO: more constraints here to make sure we don't search too little
            max_sym = min(self.state.se.max_int(s_strlen.ret_expr),
                          self.state.libc.max_symbolic_strchr)
            a, c, i = self.state.memory.find(s_addr,
                                             c,
                                             s_strlen.max_null_index,
                                             max_symbolic_bytes=max_sym,
                                             default=0)
        else:
            l.debug("concrete strlen")
            max_search = self.state.se.any_int(s_strlen.ret_expr)
            a, c, i = self.state.memory.find(s_addr, c, max_search, default=0)

        if len(i) != 0:
            a = a.annotate(MultiwriteAnnotation())
            self.state.add_constraints(*c)

        return a
コード例 #11
0
    def run(self, string):

        #additional code
        trace_data = ("puts", {"string": (string, string.symbolic)})
        try:
            self.state.procedure_data.global_variables["trace"].append(
                trace_data)
        except KeyError:
            self.state.procedure_data.global_variables["trace"] = []
            self.state.procedure_data.global_variables["trace"].append(
                trace_data)
        #end of additional code

        self.argument_types = {0: self.ty_ptr(SimTypeString())}
        self.return_type = SimTypeInt(32, True)

        write = simuvex.SimProcedures['syscalls']['write']
        strlen = simuvex.SimProcedures['libc.so.6']['strlen']

        length = self.inline_call(strlen, string).ret_expr
        self.inline_call(write, self.state.se.BVV(1, self.state.arch.bits),
                         string, length)
        self.state.posix.write(1, self.state.se.BVV(0x0a, 8), 1)

        # TODO: return values
        return self.state.se.Unconstrained('puts', self.state.arch.bits)
コード例 #12
0
    def run(self, addr_in): #pylint:disable=unused-argument
        # arg types: struct....... :(
        self.return_type = self.ty_ptr(SimTypeString())

        #TODO: return an IP address string
        ret_expr = self.state.se.Unconstrained("inet_ntoa_ret", self.state.arch.bits)
        return ret_expr
コード例 #13
0
ファイル: atoi.py プロジェクト: themaks/simuvex
    def run(self, s):
        #pylint:disable=attribute-defined-outside-init

        self.argument_types = {0: self.ty_ptr(SimTypeString())}
        self.return_type = SimTypeInt(self.state.arch, True)

        strtol = simuvex.SimProcedures['libc.so.6']['strtol']
        return strtol.strtol_inner(s, self.state, self.state.memory, 10, True)[1]
コード例 #14
0
ファイル: strncpy.py プロジェクト: themaks/simuvex
    def run(self, dst_addr, src_addr, limit, src_len=None):
        self.argument_types = {
            0: self.ty_ptr(SimTypeString()),
            1: self.ty_ptr(SimTypeString()),
            2: SimTypeLength(self.state.arch)
        }
        self.return_type = self.ty_ptr(SimTypeString())

        strlen = simuvex.SimProcedures['libc.so.6']['strlen']
        memcpy = simuvex.SimProcedures['libc.so.6']['memcpy']

        src_len = src_len if src_len is not None else self.inline_call(
            strlen, src_addr).ret_expr
        cpy_size = self.state.se.If(self.state.se.ULE(limit, src_len + 1),
                                    limit, src_len + 1)

        self.inline_call(memcpy, dst_addr, src_addr, cpy_size)
        return dst_addr
コード例 #15
0
    def run(self, p_addr, flags):
        self.argument_types = {0: self.ty_ptr(SimTypeString()),
                               1: SimTypeInt(32, True)}
        self.return_type = SimTypeFd()

        strlen = simuvex.SimProcedures['libc.so.6']['strlen']

        p_strlen = self.inline_call(strlen, p_addr)
        p_expr = self.state.memory.load(p_addr, p_strlen.max_null_index, endness='Iend_BE')
        path = self.state.se.any_str(p_expr)

        fd = self.state.posix.open(path, flags)
        return fd
コード例 #16
0
ファイル: strcasecmp.py プロジェクト: Agnishom/SummerTrace
    def run(self, a_addr, b_addr):

        #additional code
        trace_data = ("strcasecmp", {
            "a_addr": (a_addr, a_addr.symbolic),
            "b_addr": (b_addr, b_addr.symbolic)
        })
        try:
            self.state.procedure_data.global_variables["trace"].append(
                trace_data)
        except KeyError:
            self.state.procedure_data.global_variables["trace"] = []
            self.state.procedure_data.global_variables["trace"].append(
                trace_data)
        #end of additional code

        self.argument_types = {
            0: self.ty_ptr(SimTypeString()),
            1: self.ty_ptr(SimTypeString())
        }
        self.return_type = SimTypeInt(32, True)

        strlen = simuvex.SimProcedures['libc.so.6']['strlen']

        a_strlen = self.inline_call(strlen, a_addr)
        b_strlen = self.inline_call(strlen, b_addr)
        maxlen = self.state.se.BVV(
            max(a_strlen.max_null_index, b_strlen.max_null_index),
            self.state.arch.bits)

        strncmp = self.inline_call(
            simuvex.SimProcedures['libc.so.6']['strncmp'],
            a_addr,
            b_addr,
            maxlen,
            a_len=a_strlen,
            b_len=b_strlen)
        return strncmp.ret_expr
コード例 #17
0
ファイル: strlen.py プロジェクト: pyq881120/simuvex
    def run(self, s):
        #pylint:disable=attribute-defined-outside-init

        self.argument_types = {0: self.ty_ptr(SimTypeString())}
        self.return_type = SimTypeLength(self.state.arch)

        max_symbolic_bytes = self.state.libc.buf_symbolic_bytes
        max_str_len = self.state.libc.max_str_len

        if self.state.mode == 'static':

            self.max_null_index = []

            # Make sure to convert s to ValueSet
            s_list = self.state.memory.normalize_address(
                s, convert_to_valueset=True)

            length = self.state.se.ESI(self.state.arch.bits)
            for s_ptr in s_list:

                r, c, i = self.state.memory.find(
                    s,
                    self.state.se.BVV(0, 8),
                    max_str_len,
                    max_symbolic_bytes=max_symbolic_bytes)

                self.max_null_index = max(self.max_null_index + i)

                # Convert r to the same region as s
                r_list = self.state.memory.normalize_address(
                    r,
                    convert_to_valueset=True,
                    target_region=s_ptr._model_vsa.regions.keys()[0])

                for r_ptr in r_list:
                    length = length.union(r_ptr - s_ptr)

            return length

        else:
            r, c, i = self.state.memory.find(
                s,
                self.state.se.BVV(0, 8),
                max_str_len,
                max_symbolic_bytes=max_symbolic_bytes)

            self.max_null_index = max(i)
            self.state.add_constraints(*c)

            return r - s
コード例 #18
0
    def run(self, string):
        self.argument_types = {0: self.ty_ptr(SimTypeString())}
        self.return_type = SimTypeInt(32, True)

        write = simuvex.SimProcedures['syscalls']['write']
        strlen = simuvex.SimProcedures['libc.so.6']['strlen']

        length = self.inline_call(strlen, string).ret_expr
        self.inline_call(write, self.state.se.BVV(1, self.state.arch.bits),
                         string, length)
        self.state.posix.write(1, self.state.se.BVV(0x0a, 8), 1)

        # TODO: return values
        return self.state.se.Unconstrained('puts', self.state.arch.bits)
コード例 #19
0
    def run(self, s):

        #additional code
        trace_data = ("strdup", {"s": (s, s.symbolic)})
        try:
            self.state.procedure_data.global_variables["trace"].append(trace_data)
        except KeyError:
            self.state.procedure_data.global_variables["trace"] = []
            self.state.procedure_data.global_variables["trace"].append(trace_data)
        #end of additional code

        self.argument_types = {0: self.ty_ptr(SimTypeString())}
        self.return_type = self.ty_ptr(SimTypeString())

        strlen = simuvex.SimProcedures['libc.so.6']['strlen']
        strncpy = simuvex.SimProcedures['libc.so.6']['strncpy']
        malloc = simuvex.SimProcedures['libc.so.6']['malloc']

        src_len = self.inline_call(strlen, s).ret_expr
        new_s = self.inline_call(malloc, src_len+1).ret_expr

        self.inline_call(strncpy, new_s, s, src_len+1, src_len=src_len)

        return new_s
コード例 #20
0
ファイル: strncpy.py プロジェクト: Agnishom/SummerTrace
    def run(self, dst_addr, src_addr, limit, src_len=None):

        #additional code
        trace_data = ("strncpy", {"dist_addr": (dist_addr, dst_addr.symbolic), "src_addr": (src_addr, src_addr.symbolic), "limit": (limit, limit.symbolic), "src_len": (src_len, src_len.symbolic)})
        try:
            self.state.procedure_data.global_variables["trace"].append(trace_data)
        except KeyError:
            self.state.procedure_data.global_variables["trace"] = []
            self.state.procedure_data.global_variables["trace"].append(trace_data)
        #end of additional code

        self.argument_types = {0: self.ty_ptr(SimTypeString()),
                               1: self.ty_ptr(SimTypeString()),
                               2: SimTypeLength(self.state.arch)}
        self.return_type = self.ty_ptr(SimTypeString())

        strlen = simuvex.SimProcedures['libc.so.6']['strlen']
        memcpy = simuvex.SimProcedures['libc.so.6']['memcpy']

        src_len = src_len if src_len is not None else self.inline_call(strlen, src_addr).ret_expr
        cpy_size = self.state.se.If(self.state.se.ULE(limit, src_len + 1), limit, src_len + 1)

        self.inline_call(memcpy, dst_addr, src_addr, cpy_size)
        return dst_addr
コード例 #21
0
    def run(self, s_addr, c_int, s_strlen=None):

        #additional code
        trace_data = ("strchr", {
            "s_addr": (s_addr, s_addr.symbolic),
            "c_int": (c_int, c_int.symbolic)
        })
        try:
            self.state.procedure_data.global_variables["trace"].append(
                trace_data)
        except KeyError:
            self.state.procedure_data.global_variables["trace"] = []
            self.state.procedure_data.global_variables["trace"].append(
                trace_data)
        #end of additional code

        c = c_int[7:0]

        self.argument_types = {
            0: self.ty_ptr(SimTypeString()),
            1: SimTypeInt(32, True)
        }  # ?
        self.return_type = self.ty_ptr(SimTypeChar())  # ?

        s_strlen = self.inline_call(
            simuvex.SimProcedures['libc.so.6']['strlen'], s_addr)

        if self.state.se.symbolic(s_strlen.ret_expr):
            l.debug("symbolic strlen")
            # TODO: more constraints here to make sure we don't search too little
            max_sym = min(self.state.se.max_int(s_strlen.ret_expr),
                          self.state.libc.max_symbolic_strchr)
            a, c, i = self.state.memory.find(s_addr,
                                             c,
                                             s_strlen.max_null_index,
                                             max_symbolic_bytes=max_sym,
                                             default=0)
        else:
            l.debug("concrete strlen")
            max_search = self.state.se.any_int(s_strlen.ret_expr)
            a, c, i = self.state.memory.find(s_addr, c, max_search, default=0)

        if len(i) != 0:
            a = a.annotate(MultiwriteAnnotation())
            self.state.add_constraints(*c)

        return a
コード例 #22
0
ファイル: inet_ntoa.py プロジェクト: Agnishom/SummerTrace
    def run(self, addr_in): #pylint:disable=unused-argument

    	#additional code
        trace_data = ("inet_ntoa", {"addr_in": (addr_in, addr_in.symbolic)})
        try:
            self.state.procedure_data.global_variables["trace"].append(trace_data)
        except KeyError:
            self.state.procedure_data.global_variables["trace"] = []
            self.state.procedure_data.global_variables["trace"].append(trace_data)
        #end of additional code

        # arg types: struct....... :(
        self.return_type = self.ty_ptr(SimTypeString())

        #TODO: return an IP address string
        ret_expr = self.state.se.Unconstrained("inet_ntoa_ret", self.state.arch.bits)
        return ret_expr
コード例 #23
0
ファイル: strlen.py プロジェクト: themaks/simuvex
    def run(self, s):
        #pylint:disable=attribute-defined-outside-init

        self.argument_types = {0: self.ty_ptr(SimTypeString())}
        self.return_type = SimTypeLength(self.state.arch)

        max_symbolic_bytes = self.state.libc.buf_symbolic_bytes
        max_str_len = self.state.libc.max_str_len

        if self.state.mode == 'static':

            self.max_null_index = [  ]

            # Make sure to convert s to ValueSet
            s_list = self.state.memory.normalize_address(s, convert_to_valueset=True)

            length = self.state.se.ESI(self.state.arch.bits)
            for s_ptr in s_list:

                r, c, i = self.state.memory.find(s, self.state.se.BVV(0, 8), max_str_len, max_symbolic_bytes=max_symbolic_bytes)

                self.max_null_index = max(self.max_null_index + i)

                # Convert r to the same region as s
                r_list = self.state.memory.normalize_address(r, convert_to_valueset=True, target_region=s_ptr._model_vsa.regions.keys()[0])

                for r_ptr in r_list:
                    length = length.union(r_ptr - s_ptr)

            return length

        else:
            search_len = max_str_len
            r, c, i = self.state.memory.find(s, self.state.se.BVV(0, 8), search_len, max_symbolic_bytes=max_symbolic_bytes)

            # try doubling the search len and searching again
            while all(con.is_false() for con in c):
                search_len *= 2
                r, c, i = self.state.memory.find(s, self.state.se.BVV(0, 8), search_len, max_symbolic_bytes=max_symbolic_bytes)
                # stop searching after some reasonable limit
                if search_len > 0x10000:
                    raise simuvex.SimMemoryLimitError("strlen hit limit of 0x10000")

            self.max_null_index = max(i)
            self.state.add_constraints(*c)
            return r - s
コード例 #24
0
ファイル: strlen.py プロジェクト: zhuyue1314/simuvex
    def run(self, s):
        #pylint:disable=attribute-defined-outside-init

        self.argument_types = {0: self.ty_ptr(SimTypeString())}
        self.return_type = SimTypeLength(self.state.arch)

        max_symbolic_bytes = self.state.libc.buf_symbolic_bytes
        max_str_len = self.state.libc.max_str_len

        r, c, i = self.state.memory.find(s,
                                         self.state.BVV(0, 8),
                                         max_str_len,
                                         max_symbolic_bytes=max_symbolic_bytes)

        self.max_null_index = max(i)
        self.state.add_constraints(*c)
        return r - s
コード例 #25
0
ファイル: __isoc99_scanf.py プロジェクト: themaks/simuvex
    def run(self, fmt):
        #pylint:disable=attribute-defined-outside-init

        self.argument_types = {0: self.ty_ptr(SimTypeString())}
        self.return_type = SimTypeInt(self.state.arch.bits, True)

        fmt_str = self._parse(0)

        # we're reading from stdin so the region is the file's content
        f = self.state.posix.get_file(0)
        region = f.content
        start = f.pos

        (end, items) = fmt_str.interpret(start, 1, self.arg, region=region)

        # do the read, correcting the internal file position and logging the action
        self.state.posix.read_from(0, end - start)

        return items
コード例 #26
0
    def run(self, s):
        #pylint:disable=attribute-defined-outside-init

        #additional code
        trace_data = ("atoi", {"s": (s, s.symbolic)})
        try:
            self.state.procedure_data.global_variables["trace"].append(
                trace_data)
        except KeyError:
            self.state.procedure_data.global_variables["trace"] = []
            self.state.procedure_data.global_variables["trace"].append(
                trace_data)
        #end of additional code

        self.argument_types = {0: self.ty_ptr(SimTypeString())}
        self.return_type = SimTypeInt(self.state.arch, True)

        strtol = simuvex.SimProcedures['libc.so.6']['strtol']
        return strtol.strtol_inner(s, self.state, self.state.memory, 10,
                                   True)[1]
コード例 #27
0
                def run(self, s, special_addrs=None, added_constraints=None):
                    self.argument_types = {0: self.ty_ptr(SimTypeString())}
                    self.return_type = SimTypeInt(self.state.arch, True)

                    res_symb_var = claripy.BVS('atoi_ret',
                                               self.state.arch.bits)

                    # If the argument is a special constrained variable
                    s_val = self.state.se.any_int(s)
                    if s.concrete and s_val in special_addrs:
                        print(
                            "Got a special memory addr: {:X}\n".format(s_val))
                        # Grab the operator and right operand
                        (op, r_opr) = special_addrs[s_val]

                        # Add the constraint of: (return_val `op` r_opr)
                        print("Adding claripy_op_mapping[{}]({}, {})\n".format(
                            op, res_symb_var, r_opr))
                        added_constraints.append(claripy_op_mapping[op](
                            res_symb_var, r_opr))
                    return res_symb_var
コード例 #28
0
    def run(self, a_addr, b_addr, limit, a_len=None, b_len=None): #pylint:disable=arguments-differ
        # TODO: smarter types here?
        self.argument_types = {0: self.ty_ptr(SimTypeString()),
                       1: self.ty_ptr(SimTypeString()),
                       2: SimTypeLength(self.state.arch)}
        self.return_type = SimTypeInt(32, True)

        strlen = simuvex.SimProcedures['libc.so.6']['strlen']

        a_strlen = a_len if a_len is not None else self.inline_call(strlen, a_addr)
        b_strlen = b_len if b_len is not None else self.inline_call(strlen, b_addr)

        a_len = a_strlen.ret_expr
        b_len = b_strlen.ret_expr

        match_constraints = [ ]
        variables = a_len.variables | b_len.variables | limit.variables
        ret_expr = self.state.se.Unconstrained("strncmp_ret", self.state.arch.bits)

        # determine the maximum number of bytes to compare
        concrete_run = False
        #if not self.state.se.symbolic(a_len) and not self.state.se.symbolic(b_len) and not self.state.se.symbolic(limit):
        if self.state.se.single_valued(a_len) and self.state.se.single_valued(b_len) and self.state.se.single_valued(limit):
            c_a_len = self.state.se.any_int(a_len)
            c_b_len = self.state.se.any_int(b_len)
            c_limit = self.state.se.any_int(limit)

            l.debug("everything is concrete: a_len %d, b_len %d, limit %d", c_a_len, c_b_len, c_limit)

            if (c_a_len < c_limit or c_b_len < c_limit) and c_a_len != c_b_len:
                l.debug("lengths < limit and unmatched")

            concrete_run = True
            maxlen = min(c_a_len, c_b_len, c_limit)
        else:
            if self.state.se.single_valued(limit):
                c_limit = self.state.se.any_int(limit)
                maxlen = min(a_strlen.max_null_index, b_strlen.max_null_index, c_limit)
            else:
                maxlen = max(a_strlen.max_null_index, b_strlen.max_null_index)

            match_constraints.append(self.state.se.Or(a_len == b_len, self.state.se.And(self.state.se.UGE(a_len, limit), self.state.se.UGE(b_len, limit))))

        if maxlen == 0:
            # there is a corner case: if a or b are not both empty string, and limit is greater than 0, we should return
            # non-equal. Basically we only return equal when limit is 0, or a_len == b_len == 0
            if self.state.se.single_valued(limit) and self.state.se.any_int(limit) == 0:
                # limit is 0
                l.debug("returning equal for 0-limit")
                return self.state.se.BVV(0, self.state.arch.bits, variables=variables)
            elif self.state.se.single_valued(a_len) and self.state.se.single_valued(b_len) and \
                    self.state.se.any_int(a_len) == self.state.se.any_int(b_len) == 0:
                # two empty strings
                l.debug("returning equal for two empty strings")
                return self.state.se.BVV(0, self.state.arch.bits, variables=variables)
            else:
                # all other cases fall into this branch
                l.debug("returning non-equal for comparison of an empty string and a non-empty string")
                if a_strlen.max_null_index == 0:
                    return self.state.se.BVV(-1, self.state.arch.bits, variables=variables)
                else:
                    return self.state.se.BVV(1, self.state.arch.bits, variables=variables)

        # the bytes
        a_bytes = self.state.memory.load(a_addr, maxlen, endness='Iend_BE')
        b_bytes = self.state.memory.load(b_addr, maxlen, endness='Iend_BE')

        # TODO: deps

        # all possible return values in static mode
        return_values = [ ]

        for i in range(maxlen):
            l.debug("Processing byte %d", i)
            maxbit = (maxlen-i)*8
            a_byte = a_bytes[maxbit-1:maxbit-8]
            b_byte = b_bytes[maxbit-1:maxbit-8]

            if concrete_run and self.state.se.single_valued(a_byte) and self.state.se.single_valued(b_byte):
                a_conc = self.state.se.any_int(a_byte)
                b_conc = self.state.se.any_int(b_byte)
                variables |= a_byte.variables
                variables |= b_byte.variables

                if a_conc != b_conc:
                    l.debug("... found mis-matching concrete bytes 0x%x and 0x%x", a_conc, b_conc)
                    if a_conc < b_conc:
                        return self.state.se.BVV(-1, self.state.arch.bits, variables=variables)
                    else:
                        return self.state.se.BVV(1, self.state.arch.bits, variables=variables)
            else:

                if self.state.mode == 'static':
                    return_values.append(a_byte - b_byte)

                concrete_run = False

            if self.state.mode != 'static':
                byte_constraint = self.state.se.Or(a_byte == b_byte, self.state.se.ULT(a_len, i), self.state.se.ULT(limit, i))
                match_constraints.append(byte_constraint)

        if concrete_run:
            l.debug("concrete run made it to the end!")
            return self.state.se.BVV(0, self.state.arch.bits, variables=variables)

        if self.state.mode == 'static':
            ret_expr = self.state.se.ESI(8)
            for expr in return_values:
                ret_expr = ret_expr.union(expr)

            ret_expr = ret_expr.sign_extend(self.state.arch.bits - 8)

        else:
            # make the constraints

            l.debug("returning symbolic")
            match_constraint = self.state.se.And(*match_constraints)
            nomatch_constraint = self.state.se.Not(match_constraint)

            #l.debug("match constraints: %s", match_constraint)
            #l.debug("nomatch constraints: %s", nomatch_constraint)

            match_case = self.state.se.And(limit != 0, match_constraint, ret_expr == 0)
            nomatch_case = self.state.se.And(limit != 0, nomatch_constraint, ret_expr == 1)
            l0_case = self.state.se.And(limit == 0, ret_expr == 0)
            empty_case = self.state.se.And(a_strlen.ret_expr == 0, b_strlen.ret_expr == 0, ret_expr == 0)

            self.state.add_constraints(self.state.se.Or(match_case, nomatch_case, l0_case, empty_case))

        return ret_expr
コード例 #29
0
    def run(self,
            str_ptr,
            delim_ptr,
            save_ptr,
            str_strlen=None,
            delim_strlen=None):

        #additional code
        trace_data = ("strtok_r", {
            "str_ptr": (str_ptr, str_ptr.symbolic),
            "delim_ptr": (delim_ptr, delim_ptr.symbolic),
            "save_ptr": (save_ptr, save_ptr.symbolic),
            "str_strlen": (str_strlen, str_strlen.symbolic),
            "delim_strlen": (delim_strlen, delim_strlen.symbolic)
        })
        try:
            self.state.procedure_data.global_variables["trace"].append(
                trace_data)
        except KeyError:
            self.state.procedure_data.global_variables["trace"] = []
            self.state.procedure_data.global_variables["trace"].append(
                trace_data)
        #end of additional code

        self.argument_types = {
            0: self.ty_ptr(SimTypeString()),
            1: self.ty_ptr(SimTypeString()),
            2: self.ty_ptr(self.ty_ptr(SimTypeString()))
        }
        self.return_type = self.ty_ptr(SimTypeString())

        if self.state.libc.simple_strtok:
            malloc = simuvex.SimProcedures['libc.so.6']['malloc']
            token_ptr = self.inline_call(
                malloc, self.state.libc.strtok_token_size).ret_expr
            r = self.state.se.If(
                self.state.se.Unconstrained('strtok_case',
                                            self.state.arch.bits) == 0,
                token_ptr, self.state.se.BVV(0, self.state.arch.bits))
            self.state.libc.strtok_heap.append(token_ptr)
            return r
        else:
            strstr = simuvex.SimProcedures['libc.so.6']['strstr']
            strlen = simuvex.SimProcedures['libc.so.6']['strlen']

            l.debug("Doin' a strtok_r!")
            l.debug("... geting the saved state")

            saved_str_ptr = self.state.memory.load(
                save_ptr,
                self.state.arch.bytes,
                endness=self.state.arch.memory_endness)
            start_ptr = self.state.se.If(str_ptr == 0, saved_str_ptr, str_ptr)

            l.debug("... getting the lengths")
            str_strlen = self.inline_call(
                strlen, start_ptr) if str_strlen is None else str_strlen
            delim_strlen = self.inline_call(
                strlen, delim_ptr) if delim_strlen is None else delim_strlen

            l.debug(
                "... STRTOK SLOW PATH (symbolic-length delimiteter and/or string)"
            )
            l.debug("... calling strstr")
            where = self.inline_call(strstr,
                                     start_ptr,
                                     delim_ptr,
                                     haystack_strlen=str_strlen,
                                     needle_strlen=delim_strlen)
            write_length = self.state.se.If(where.ret_expr != 0,
                                            delim_strlen.ret_expr, 0)
            write_content = self.state.se.BVV(0,
                                              delim_strlen.max_null_index * 8)

            # do a symbolic write (we increment the limit because of the possibility that the write target is 0, in which case the length will be 0, anyways)
            l.debug("... doing the symbolic write")
            self.state.memory.store(where.ret_expr,
                                    write_content,
                                    size=write_length,
                                    strategy=["symbolic_nonzero", "any"],
                                    limit=str_strlen.max_null_index + 1)

            l.debug("... creating the return address")
            new_start = write_length + where.ret_expr
            new_state = self.state.se.If(new_start != 0, new_start, start_ptr)

            l.debug("... saving the state")
            self.state.memory.store(save_ptr,
                                    new_state,
                                    endness=self.state.arch.memory_endness)

            l.debug("... done")
            return new_start
コード例 #30
0
    def run(self, a_addr, b_addr, limit, a_len=None, b_len=None): #pylint:disable=arguments-differ
        # TODO: smarter types here?
        self.argument_types = {0: self.ty_ptr(SimTypeString()),
                       1: self.ty_ptr(SimTypeString()),
                       2: SimTypeLength(self.state.arch)}
        self.return_type = SimTypeInt(32, True)

        strlen = simuvex.SimProcedures['libc.so.6']['strlen']

        a_strlen = a_len if a_len is not None else self.inline_call(strlen, a_addr)
        b_strlen = b_len if b_len is not None else self.inline_call(strlen, b_addr)

        a_len = a_strlen.ret_expr
        b_len = b_strlen.ret_expr

        match_constraints = [ ]
        variables = a_len.variables | b_len.variables | limit.variables
        ret_expr = self.state.se.Unconstrained("strncmp_ret", self.state.arch.bits)

        # determine the maximum number of bytes to compare
        concrete_run = False
        if not self.state.se.symbolic(a_len) and not self.state.se.symbolic(b_len) and not self.state.se.symbolic(limit):
            c_a_len = self.state.se.any_int(a_len)
            c_b_len = self.state.se.any_int(b_len)
            c_limit = self.state.se.any_int(limit)

            l.debug("everything is concrete: a_len %d, b_len %d, limit %d", c_a_len, c_b_len, c_limit)

            if (c_a_len < c_limit or c_b_len < c_limit) and c_a_len != c_b_len:
                l.debug("lengths < limit and unmatched")
                return self.state.se.BVV(1, self.state.arch.bits, variables=variables)

            concrete_run = True
            maxlen = min(c_a_len, c_b_len, c_limit)
        else:
            if not self.state.se.symbolic(limit):
                c_limit = self.state.se.any_int(limit)
                maxlen = min(a_strlen.max_null_index, b_strlen.max_null_index, c_limit)
            else:
                maxlen = max(a_strlen.max_null_index, b_strlen.max_null_index)

            match_constraints.append(self.state.se.Or(a_len == b_len, self.state.se.And(self.state.se.UGE(a_len, limit), self.state.se.UGE(b_len, limit))))

        if maxlen == 0:
            l.debug("returning equal for 0-length maximum strings")
            return self.state.se.BVV(0, self.state.arch.bits, variables=variables)

        # the bytes
        a_bytes = self.state.memory.load(a_addr, maxlen, endness='Iend_BE')
        b_bytes = self.state.memory.load(b_addr, maxlen, endness='Iend_BE')

        # TODO: deps
        for i in range(maxlen):
            l.debug("Processing byte %d", i)
            maxbit = (maxlen-i)*8
            a_byte = a_bytes[maxbit-1:maxbit-8]
            b_byte = b_bytes[maxbit-1:maxbit-8]

            if concrete_run and not self.state.se.symbolic(a_byte) and not self.state.se.symbolic(b_byte):
                a_conc = self.state.se.any_int(a_byte)
                b_conc = self.state.se.any_int(b_byte)
                variables |= a_byte.variables
                variables |= b_byte.variables

                if a_conc != b_conc:
                    l.debug("... found mis-matching concrete bytes 0x%x and 0x%x", a_conc, b_conc)
                    return self.state.se.BVV(1, self.state.arch.bits, variables=variables)
            else:
                concrete_run = False

            byte_constraint = self.state.se.Or(a_byte == b_byte, self.state.se.ULT(a_len, i), self.state.se.ULT(limit, i))
            match_constraints.append(byte_constraint)

        if concrete_run:
            l.debug("concrete run made it to the end!")
            return self.state.se.BVV(0, self.state.arch.bits, variables=variables)

        # make the constraints
        l.debug("returning symbolic")
        match_constraint = self.state.se.And(*match_constraints)
        nomatch_constraint = self.state.se.Not(match_constraint)

        #l.debug("match constraints: %s", match_constraint)
        #l.debug("nomatch constraints: %s", nomatch_constraint)

        match_case = self.state.se.And(limit != 0, match_constraint, ret_expr == 0)
        nomatch_case = self.state.se.And(limit != 0, nomatch_constraint, ret_expr == 1)
        l0_case = self.state.se.And(limit == 0, ret_expr == 0)
        empty_case = self.state.se.And(a_strlen.ret_expr == 0, b_strlen.ret_expr == 0, ret_expr == 0)

        self.state.add_constraints(self.state.se.Or(match_case, nomatch_case, l0_case, empty_case))
        return ret_expr