docstr: Returns:
  
  visible_vars: Vars from lexical scopes visible at the beginning of the
  block, up to but not including outputs from before_op. Given program:
  
  #    main(%a: (1, 2, fp32),
  #         %b: (1, 2, fp32),
  #         %c: (1, 2, fp32)) {
  #      block0() {
  #        %const1: (1, fp32) = const(...)
  #        %loop:0: (1, 2, fp32), %loop:1: (1, 2, fp32) =         #        while_loop(loop_vars=(%a, %b))
  #          loop_cond(%a.x, %b.x) {
  #            %blah: (bool) = some_op(x=%a.x, y=%b.x)
  #            %cond_var: (bool) = some_op2(x=%a.x, y=%blah)
  #          } -> (%cond_var)
  #          loop_body(%a.x, %b.x) {
  #            %add_0: (1, 2, fp32) = add(x=%a.x, y=%b.x)
  #          } -> (%add_0, %b.x)
  #        %const2: (1, fp32) = const(...)
  #      } -> (%loop:0, %loop:1)
  #    }
  
  Let V0 be the set of internal_vars of block0 block that supplies const
  vals (for const).
  
  Ex1: self = block0
      visible_vars = {%a, %b, %c} (function input)
  
  Ex2: self = loop_cond.
      visible_vars = {%a, %b, %c, %const1, V0} (Note that %const2 is not
      part of the set)
docstr_tok: ["Returns",":","visible_vars",":","Vars","from","lexical","scopes","visible","at","the","beginning","of","the","block",",","up","to","but","not","including","outputs","from","before_op",".","Given","program",":","#","main","(","%","a",":","(","1",",","2",",","fp32",")",",","#","%","b",":","(","1",",","2",",","fp32",")",",","#","%","c",":","(","1",",","2",",","fp32",")",")","{","#","block0","(",")","{","#","%","const1",":","(","1",",","fp32",")","=","const","(","...",")","#","%","loop:0",":","(","1",",","2",",","fp32",")",",","%","loop:1",":","(","1",",","2",",","fp32",")","=","#","while_loop","(","loop_vars=","(","%","a",",","%","b",")",")","#","loop_cond","(","%","a.x",",","%","b.x",")","{","#","%","blah",":","(","bool",")","=","some_op","(","x=","%","a.x",",","y=","%","b.x",")","#","%","cond_var",":","(","bool",")","=","some_op2","(","x=","%","a.x",",","y=","%","blah",")","#","}","-",">","(","%","cond_var",")","#","loop_body","(","%","a.x",",","%","b.x",")","{","#","%","add_0",":","(","1",",","2",",","fp32",")","=","add","(","x=","%","a.x",",","y=","%","b.x",")","#","}","-",">","(","%","add_0",",","%","b.x",")","#","%","const2",":","(","1",",","fp32",")","=","const","(","...",")","#","}","-",">","(","%","loop:0",",","%","loop:1",")","#","}","Let","V0","be","the","set","of","internal_vars","of","block0","block","that","supplies","const","vals","(","for","const",")",".","Ex1",":","self","=","block0","visible_vars","=","{","%","a",",","%","b",",","%","c","}","(","function","input",")","Ex2",":","self","=","loop_cond",".","visible_vars","=","{","%","a",",","%","b",",","%","c",",","%","const1",",","V0","}","(","Note","that","%","const2","is","not","part","of","the","set",")"]
code: def _visible_vars_from_enclosing_block(self):
      """
          Returns:
  
          visible_vars: Vars from lexical scopes visible at the beginning of the
          block, up to but not including outputs from before_op. Given program:
  
          #    main(%a: (1, 2, fp32),
          #         %b: (1, 2, fp32),
          #         %c: (1, 2, fp32)) {
          #      block0() {
          #        %const1: (1, fp32) = const(...)
          #        %loop:0: (1, 2, fp32), %loop:1: (1, 2, fp32) = \
          #        while_loop(loop_vars=(%a, %b))
          #          loop_cond(%a.x, %b.x) {
          #            %blah: (bool) = some_op(x=%a.x, y=%b.x)
          #            %cond_var: (bool) = some_op2(x=%a.x, y=%blah)
          #          } -> (%cond_var)
          #          loop_body(%a.x, %b.x) {
          #            %add_0: (1, 2, fp32) = add(x=%a.x, y=%b.x)
          #          } -> (%add_0, %b.x)
          #        %const2: (1, fp32) = const(...)
          #      } -> (%loop:0, %loop:1)
          #    }
  
          Let V0 be the set of internal_vars of block0 block that supplies const
          vals (for const).
  
          Ex1: self = block0
              visible_vars = {%a, %b, %c} (function input)
  
          Ex2: self = loop_cond.
              visible_vars = {%a, %b, %c, %const1, V0} (Note that %const2 is not
              part of the set)
          """
      visible_vars = set()
  
      # function inputs are considered external to the block.
      if isinstance(self, Function):
          # block in function only has function_inputs as from enclosing
          # block (Ex1 above).
          visible_vars.update(self.function_inputs)
          return visible_vars
  
      if self.outer_op is not None:
          enclosing_block = self.outer_op.enclosing_block
          vars_at_start = (
              enclosing_block._visible_vars_from_enclosing_block()
          )
          visible_vars.update(vars_at_start)
          (
              _,
              visible_vars_in_block,
          ) = enclosing_block._visible_vars_in_block(
              self.outer_op, inclusive=False
          )
          visible_vars.update(visible_vars_in_block)
  
      return visible_vars
  
imports: from collections import Counter, OrderedDict
  import copy
  import logging
  import numpy
  from six import string_types
  from .None import SPACES, types
  from .var import Var, InternalVar, ListVar
  from .visitors.dot_visitor import DotVisitor
  from .types.symbolic import k_used_symbols, k_num_internal_syms, any_symbolic, is_symbolic
  from .input_type import TupleInputType
label_desc: Use image node_id 13 for calling the Block obj's underlying member method code with example usage: obj._visible_vars_from_enclosing_block() and returns: visible_vars, visible_vars