示例#1
0
def Sum(*args: BitVec) -> BitVec:
    """Create sum expression.

    :return:
    """
    raw = z3.Sum([a.raw for a in args])
    annotations = []  # type: Annotations
    bitvecfuncs = []

    for bv in args:
        annotations += bv.annotations
        if isinstance(bv, BitVecFunc):
            bitvecfuncs.append(bv)

    if len(bitvecfuncs) >= 2:
        return BitVecFunc(raw=raw,
                          func_name=None,
                          input_=None,
                          annotations=annotations)
    elif len(bitvecfuncs) == 1:
        return BitVecFunc(
            raw=raw,
            func_name=bitvecfuncs[0].func_name,
            input_=bitvecfuncs[0].input_,
            annotations=annotations,
        )

    return BitVec(raw, annotations)
示例#2
0
def Concat(*args: Union[BitVec, List[BitVec]]) -> BitVec:
    """Create a concatenation expression.

    :param args:
    :return:
    """
    # The following statement is used if a list is provided as an argument to concat
    if len(args) == 1 and isinstance(args[0], list):
        bvs = args[0]  # type: List[BitVec]
    else:
        bvs = cast(List[BitVec], args)

    nraw = z3.Concat([a.raw for a in bvs])
    annotations = []  # type: Annotations
    bitvecfunc = False
    for bv in bvs:
        annotations += bv.annotations
        if isinstance(bv, BitVecFunc):
            bitvecfunc = True

    if bitvecfunc:
        # Is there a better value to set func_name and input to in this case?
        return BitVecFunc(raw=nraw,
                          func_name=None,
                          input_=None,
                          annotations=annotations)

    return BitVec(nraw, annotations)
示例#3
0
def Concat(*args: Union[BitVec, List[BitVec]]) -> BitVec:
    """Create a concatenation expression.

    :param args:
    :return:
    """
    # The following statement is used if a list is provided as an argument to concat
    if len(args) == 1 and isinstance(args[0], list):
        bvs = args[0]  # type: List[BitVec]
    else:
        bvs = cast(List[BitVec], args)

    nraw = z3.Concat([a.raw for a in bvs])
    annotations = set()  # type: Annotations

    nested_functions = []  # type: List[BitVecFunc]
    for bv in bvs:
        annotations = annotations.union(bv.annotations)
        if isinstance(bv, BitVecFunc):
            nested_functions += bv.nested_functions
            nested_functions += [bv]

    if nested_functions:
        return BitVecFunc(
            raw=nraw,
            func_name="Hybrid",
            input_=BitVec(z3.BitVec("", 256), annotations=annotations),
            nested_functions=nested_functions,
        )

    return BitVec(nraw, annotations)
示例#4
0
def Concat(*args: Union[BitVec, List[BitVec]]) -> BitVec:
    """Create a concatenation expression.

    :param args:
    :return:
    """
    # The following statement is used if a list is provided as an argument to concat
    if len(args) == 1 and isinstance(args[0], list):
        bvs = args[0]  # type: List[BitVec]
    else:
        bvs = cast(List[BitVec], args)

    nraw = z3.Concat([a.raw for a in bvs])
    annotations = set()  # type: Annotations
    bitvecfunc = False
    for bv in bvs:
        annotations = annotations.union(bv.annotations)
        if isinstance(bv, BitVecFunc):
            bitvecfunc = True

    if bitvecfunc:
        # Added this not so good and misleading NOTATION to help with this
        str_hash = ",".join(["hashed({})".format(hash(bv)) for bv in bvs])
        input_string = "MisleadingNotationConcat({})".format(str_hash)

        return BitVecFunc(raw=nraw,
                          func_name="Hybrid",
                          input_=BitVec(z3.BitVec(input_string, 256),
                                        annotations=annotations))

    return BitVec(nraw, annotations)
示例#5
0
 def BitVecFuncSym(
     name: str,
     func_name: str,
     size: int,
     annotations: Annotations = None,
     input_: Union[int, "BitVec"] = None,
 ) -> BitVecFunc:
     """Creates a new bit vector function with a symbolic value."""
     raw = z3.BitVec(name, size)
     return BitVecFunc(raw, func_name, input_, annotations)
示例#6
0
 def BitVecFuncVal(
     value: int,
     func_name: str,
     size: int,
     annotations: Annotations = None,
     input_: Union[int, "BitVec"] = None,
 ) -> BitVecFunc:
     """Creates a new bit vector function with a concrete value."""
     raw = z3.BitVecVal(value, size)
     return BitVecFunc(raw, func_name, input_, annotations)
示例#7
0
def _arithmetic_helper(a: BitVec, b: BitVec, operation: Callable) -> BitVec:
    raw = operation(a.raw, b.raw)
    union = a.annotations + b.annotations

    if isinstance(a, BitVecFunc) and isinstance(b, BitVecFunc):
        return BitVecFunc(raw=raw,
                          func_name=None,
                          input_=None,
                          annotations=union)
    elif isinstance(a, BitVecFunc):
        return BitVecFunc(raw=raw,
                          func_name=a.func_name,
                          input_=a.input_,
                          annotations=union)
    elif isinstance(b, BitVecFunc):
        return BitVecFunc(raw=raw,
                          func_name=b.func_name,
                          input_=b.input_,
                          annotations=union)

    return BitVec(raw, annotations=union)
示例#8
0
def Sum(*args: BitVec) -> BitVec:
    """Create sum expression.

    :return:
    """
    raw = z3.Sum([a.raw for a in args])
    annotations = set()  # type: Annotations
    bitvecfuncs = []

    for bv in args:
        annotations = annotations.union(bv.annotations)
        if isinstance(bv, BitVecFunc):
            bitvecfuncs.append(bv)

    nested_functions = [
        nf for func in bitvecfuncs for nf in func.nested_functions
    ] + bitvecfuncs

    if len(bitvecfuncs) >= 2:
        return BitVecFunc(
            raw=raw,
            func_name="Hybrid",
            input_=None,
            annotations=annotations,
            nested_functions=nested_functions,
        )
    elif len(bitvecfuncs) == 1:
        return BitVecFunc(
            raw=raw,
            func_name=bitvecfuncs[0].func_name,
            input_=bitvecfuncs[0].input_,
            annotations=annotations,
            nested_functions=nested_functions,
        )

    return BitVec(raw, annotations)
示例#9
0
def Extract(high: int, low: int, bv: BitVec) -> BitVec:
    """Create an extract expression.

    :param high:
    :param low:
    :param bv:
    :return:
    """
    raw = z3.Extract(high, low, bv.raw)
    if isinstance(bv, BitVecFunc):
        # Is there a better value to set func_name and input to in this case?
        return BitVecFunc(raw=raw,
                          func_name=None,
                          input_=None,
                          annotations=bv.annotations)

    return BitVec(raw, annotations=bv.annotations)
示例#10
0
def Extract(high: int, low: int, bv: BitVec) -> BitVec:
    """Create an extract expression.

    :param high:
    :param low:
    :param bv:
    :return:
    """
    raw = z3.Extract(high, low, bv.raw)
    if isinstance(bv, BitVecFunc):
        input_string = "MisleadingNotationExtract({}, {}, hashed({}))".format(
            high, low, hash(bv))
        # Is there a better value to set func_name and input to in this case?
        return BitVecFunc(raw=raw,
                          func_name="Hybrid",
                          input_=BitVec(z3.BitVec(input_string, 256),
                                        annotations=bv.annotations))

    return BitVec(raw, annotations=bv.annotations)
示例#11
0
def Extract(high: int, low: int, bv: BitVec) -> BitVec:
    """Create an extract expression.

    :param high:
    :param low:
    :param bv:
    :return:
    """
    raw = z3.Extract(high, low, bv.raw)
    if isinstance(bv, BitVecFunc):
        input_string = ""
        # Is there a better value to set func_name and input to in this case?
        return BitVecFunc(
            raw=raw,
            func_name="Hybrid",
            input_=BitVec(z3.BitVec(input_string, 256),
                          annotations=bv.annotations),
            nested_functions=bv.nested_functions + [bv],
        )

    return BitVec(raw, annotations=bv.annotations)
示例#12
0
def If(a: Union[Bool, bool], b: Union[BitVec, int], c: Union[BitVec,
                                                             int]) -> BitVec:
    """Create an if-then-else expression.

    :param a:
    :param b:
    :param c:
    :return:
    """
    # TODO: Handle BitVecFunc

    if not isinstance(a, Bool):
        a = Bool(z3.BoolVal(a))
    if not isinstance(b, BitVec):
        b = BitVec(z3.BitVecVal(b, 256))
    if not isinstance(c, BitVec):
        c = BitVec(z3.BitVecVal(c, 256))
    union = a.annotations.union(b.annotations).union(c.annotations)

    bvf = []  # type: List[BitVecFunc]
    if isinstance(a, BitVecFunc):
        bvf += [a]
    if isinstance(b, BitVecFunc):
        bvf += [b]
    if isinstance(c, BitVecFunc):
        bvf += [c]
    if bvf:
        raw = z3.If(a.raw, b.raw, c.raw)
        nested_functions = [
            nf for func in bvf for nf in func.nested_functions
        ] + bvf
        return BitVecFunc(raw,
                          func_name="Hybrid",
                          nested_functions=nested_functions)

    return BitVec(z3.If(a.raw, b.raw, c.raw), union)