def _scan_nodes(nodelist, context, instance_types, current_block=None, ignore_blocks=None):
    results = []
    for node in nodelist:
        if isinstance(node, instance_types):
            results.append(node)
        elif isinstance(node, IncludeNode):
            if node.template:
                if not callable(getattr(node.template, 'render', None)):
                    template = get_template(node.template.var)
                else:
                    template = node.template
                if TemplateAdapter is not None and isinstance(template, TemplateAdapter):
                    template = template.template
                results += _scan_nodes(template.nodelist, context, instance_types, current_block)
        elif isinstance(node, ExtendsNode):
            results += _extend_nodelist(node, context, instance_types)
        elif isinstance(node, VariableNode) and current_block:
            if node.filter_expression.token == 'block.super':
                if not hasattr(current_block.parent, 'nodelist'):
                    raise TemplateSyntaxError(
                        "Cannot read {{{{ block.super }}}} for {{% block {0} %}}, "
                        "the parent template doesn't have this block.".format(
                        current_block.name
                    ))
                results += _scan_nodes(current_block.parent.nodelist, context, instance_types, current_block.parent)
        elif isinstance(node, BlockNode) and ignore_blocks and node.name in ignore_blocks:
            continue
        elif hasattr(node, 'child_nodelists'):
            for nodelist_name in node.child_nodelists:
                if hasattr(node, nodelist_name):
                    subnodelist = getattr(node, nodelist_name)
                    if isinstance(subnodelist, NodeList):
                        if isinstance(node, BlockNode):
                            current_block = node
                        results += _scan_nodes(subnodelist, context, instance_types, current_block)
        else:
            for attr in dir(node):
                obj = getattr(node, attr)
                if isinstance(obj, NodeList):
                    if isinstance(node, BlockNode):
                        current_block = node
                    results += _scan_nodes(obj, context, instance_types, current_block)
    return results