def join(cls, a: 'Variable', b: 'Variable') -> 'Variable': """ Return a Variable whose values and def sites are the unions of the inputs value and def site sets. """ vals = ssle.join(a, b) sites = ssle.join(a.def_sites, b.def_sites) if vals.is_top: return cls.top(def_sites=sites) return cls(values=vals, def_sites=sites)
def bottom(cls, name=VAR_DEFAULT_NAME, def_sites: ssle = ssle.bottom()) -> 'Variable': """ Return a Variable with Bottom value, and optionally set its name. Args: name: the name of the new variable. def_sites: a set of locations where this variable was possibly defined. """ return cls(values=cls._bottom_val(), name=name, def_sites=def_sites)
def top(cls, name=VAR_DEFAULT_NAME, def_sites: ssle = ssle.bottom()) -> 'Variable': """ Return a Variable with Top value, and optionally set its name. Args: name: the name of the new variable. def_sites: a set of locations where this variable was possibly defined. """ result = cls(name=name, def_sites=def_sites) result.value = cls._top_val() return result
def arith_op(cls, opname: str, args: t.Iterable['Variable'], name=VAR_RESULT_NAME) -> 'Variable': """ Apply the named arithmetic operation to the given Variables' values in all permutations, and return a Variable containing the result. Args: opname: the EVM operation to apply. args: a sequence of Variables whose length matches the arity of the specified operation. name: the name of the result Variable. """ result = ssle.cartesian_map(getattr(cls, opname), args) return cls(values=result, name=name)
def __init__(self, values: t.Iterable = None, name: str = VAR_DEFAULT_NAME, def_sites: ssle = ssle.bottom()): """ Args: values: the set of values this variable could take. name: the name that uniquely identifies this variable. def_sites: a set of locations (TACLocRefs) where this variable was possibly defined. """ # Make sure the input values are not out of range. mod = [] if values is None else [v % self.CARDINALITY for v in values] super().__init__(value=mod) self.name = name self.def_sites = def_sites
def __init__(self, name: str, payload=None, def_sites: ssle = ssle.bottom()): """ Args: name: the name of the new MetaVariable payload: some information to carry along with this MetaVariable. def_sites: a set of locations where this variable was possibly defined. """ super().__init__(values=self._bottom_val(), name=name, def_sites=def_sites) self.value = self._top_val() """ The value of this MetaVariable. MetaVariables are taken to have unconstrained value sets. """ self.payload = payload
def values(self) -> ssle: """ Return the set of values this location may contain. Generically, this set is unconstrained. """ return ssle.top()
def __new_metavar(n: int, def_sites: ssle = ssle.bottom()) -> MetaVariable: """Return a MetaVariable with the given payload and a corresponding name.""" return MetaVariable(name="S{}".format(n), payload=n, def_sites=def_sites)