def read_macro_constant(node): extent = node.extent start, end = extent.start, extent.end with open(start.file.name) as fd: a = start.offset + len(node.displayname) b = end.offset data = fd.read()[a:b].strip() if data.isdigit(): return objects.Integer(int(data)) if data.startswith('0x'): return objects.Integer(int(data, 16)) if data.startswith('"') and data.endswith('"'): return objects.String(data[1:-1]) raise Exception("no interpretation found for %r" % data)
def expr(self, expr): if expr.type == 'identifier': var = self.function.lookup(expr.string) assert var is not None, repr(expr.string) return var if expr.type == 'string': return objects.String(expr.string) if expr.type == 'number': if "." in expr.string: return objects.Float(float(expr.string)) elif expr.string.startswith('0x'): return objects.Integer(int(expr.string, 16)) else: return objects.Integer(int(expr.string)) if expr.type == 'member': arg = self.expr(expr[0]) return self.append(member(arg, expr.string)) if expr.type == 'call': args = [self.expr(sub_expr) for sub_expr in expr] callee = args.pop(0) return self.append(call(callee, args)) if expr.type == 'def': argv = [arg.string for arg in expr[0]] body = expr[1:] return self.new_function(argv, body) if expr.type == 'op': lhs, rhs = expr opname = '' if expr.string == '<': opname = 'lt' if expr.string == '>': opname = 'gt' if expr.string == '<=': opname = 'le' if expr.string == '>=': opname = 'ge' if expr.string == '!=': opname = 'ne' if expr.string == '==': opname = 'eq' if len(opname) > 0: res = call(self.function.lookup(opname), [self.expr(lhs), self.expr(rhs)]) self.append(res) return res raise Exception("%s not built" % expr.repr())
def from_ctypes(self, value): if isinstance(value, (int, long)): return objects.Integer(value) if isinstance(value, float): return objects.Float(value) if value is None: return objects.null raise Exception("Unknown cell value: %r" % value)
def read_enum_constant(node, parent): const = objects.Integer(0) for item in parent.get_children(): for info in item.get_children(): assert info.kind == CursorKind.INTEGER_LITERAL const = read_macro_constant(info) if node.spelling == item.spelling: return const const.value += 1 raise Exception("odd or invalid input for this function")
def eval_binary_op(self, ast_node, env): op = ast_node.op # left = self.eval_expression(ast_node.left, env) left = self.eval(ast_node.left, env) # right = self.eval_expression(ast_node.right, env) right = self.eval(ast_node.right, env) if isinstance(op, tokens.PLUS): return objects.Integer(left + right) if isinstance(op, tokens.MINUS): return objects.Integer(left - right) if isinstance(op, tokens.ASTERISK): return objects.Integer(left * right) if isinstance(op, tokens.SLASH): return objects.Integer(left / right) if isinstance(op, tokens.EQ): if left == right: return objects.TRUE return objects.FALSE if isinstance(op, tokens.NEQ): if left != right: return objects.TRUE return objects.FALSE if isinstance(op, tokens.GT): if left > right: return objects.TRUE return objects.FALSE if isinstance(op, tokens.LT): if left < right: return objects.TRUE return objects.FALSE if isinstance(op, tokens.GTE): if left >= right: return objects.TRUE return objects.FALSE if isinstance(op, tokens.LTE): if left <= right: return objects.TRUE return objects.FALSE
def compile_integer(context, ast): assert(isinstance(ast,ast_objects.Integer)) value = objects.Integer(ast.value) index = context.register_constant(value) context.emit(bytecode.LOAD_CONST,index)
def eval_int_literal(self, ast_node, env): value = int(ast_node.literal) return objects.Integer(value)
def eval_prefix_op(self, ast_node, env): op = ast_node.op right = self.eval_expression(ast_node.right, env) if isinstance(op, tokens.MINUS): return objects.Integer(-right)
def from_ctypes(self, value): return objects.Integer(value)
def sub(a, b): if isinstance(a, objects.Float) or isinstance(b, objects.Float): return objects.Float(a.value - b.value) if isinstance(a, objects.Integer) and isinstance(b, objects.Integer): return objects.Integer(a.value - b.value) raise Exception("cannot subtract %r, %r" % (a, b))