def unit(self, node): """ Return the analysis unit that owns `node`. :param AbstractExpression node: Node for which we want the embedding analysis unit. :rtype: ResolvedExpression """ node_expr = construct(node) # Automatically extract AST nodes from entities if node_expr.type.is_entity_type: node_expr = FieldAccessExpr(node_expr, 'El', node_expr.type.el_type, do_explicit_incref=True) # Make sure that in the end, the prefix is an AST node check_source_language( node_expr.type.is_ast_node, 'The "unit" field is available only for AST nodes; instead we have' ' here a {}'.format(node_expr.type.name.lower) ) # From the point of view of properties, analysis units are not ref-counted, # so we must not inc-ref here. return FieldAccessExpr(node_expr, 'Unit', T.AnalysisUnitType, do_explicit_incref=False, abstract_expr=self)
def parent(self, node): """ Return `node`'s parent in the AST. This works on both bare nodes and entities. .. todo:: Implement rebindings shedding. """ node_expr = construct(node) check_source_language( node_expr.type.is_ast_node or node_expr.type.is_entity_type, 'Invalid prefix for "parent": got {} but AST node or entity' ' expected'.format(node_expr.type.dsl_name)) if node_expr.type.is_entity_type: return FieldAccess.Expr(node_expr, get_builtin_field('parent'), [], implicit_deref=True, abstract_expr=self) else: return FieldAccessExpr(node_expr, 'Parent', T.root_node, do_explicit_incref=False, abstract_expr=self)
def analysis_unit_root(self, unit): """ Return `unit`'s root AST node. :param ResolvedExpression unit: Expression that yields the analysis unit for which we want to extract the root AST node. """ unit_expr = NullCheckExpr(construct(unit, T.AnalysisUnitType)) return FieldAccessExpr(unit_expr, 'AST_Root', T.root_node, do_explicit_incref=False, abstract_expr=self)
def rebindings_parent(self, rebindings): """ Return the parent rebindings for `rebindings`. :param AbstractExpression rebindings: Input expression, must evaluate to a rebindings. :rtype: ResolvedExpression """ return FieldAccessExpr(construct_non_null_rebindings(rebindings), 'Parent', T.EnvRebindingsType, do_explicit_incref=False, abstract_expr=self)
def rebindings_new_env(self, rebindings): """ Return the lexical environment that `rebindings` remaps to. :param AbstractExpression rebindings: Input expression, must evaluate to a rebindings. :rtype: ResolvedExpression """ return FieldAccessExpr(construct_non_null_rebindings(rebindings), 'New_Env', T.LexicalEnvType, do_explicit_incref=True, abstract_expr=self)
def unit(node): """ Expression that gets the analysis unit that "node_expr" belongs to. :param AbstractExpression node: Node for which we want the embedding analysis unit. :rtype: AbstractExpression """ node_expr = construct(node) check_source_language( issubclass(node_expr.type, T.root_node), 'The "unit" field is available only for AST nodes; instead we have' ' here a {}'.format(node_expr.type.name().lower)) return FieldAccessExpr(node_expr, 'Unit', AnalysisUnitType)
def length(self, collection): """ Compute the length of `collection`. """ coll_expr = construct(collection) orig_type = coll_expr.type if coll_expr.type.is_entity_type: coll_expr = FieldAccessExpr(coll_expr, 'Node', coll_expr.type.astnode, do_explicit_incref=False) check_source_language( coll_expr.type.is_collection, 'Collection expected but got {} instead'.format(orig_type.dsl_name)) return CallExpr('Len', 'Length', T.Int, [coll_expr], abstract_expr=self)
def length(self: AbstractExpression, collection: AbstractExpression) -> ResolvedExpression: """ Compute the length of `collection`. """ coll_expr = construct(collection) orig_type = coll_expr.type # Automatically unwrap entities if coll_expr.type.is_entity_type: coll_expr = FieldAccessExpr(coll_expr, 'Node', coll_expr.type.astnode, do_explicit_incref=False) check_source_language( coll_expr.type.is_collection, 'Collection expected but got {} instead'.format(orig_type.dsl_name)) coll_expr, _ = canonicalize_list(coll_expr) return CallExpr('Len', 'Length', T.Int, [coll_expr], abstract_expr=self)