# Path: cmd_ir/core_types.py
# class InsnArg:
# 
#     @classmethod
#     def _init_from_parser(cls, value):
#         return value
# 
# class NativeType(InsnArg):
# 
#     @classmethod
#     def typename(cls):
#         return cls.__name__
# 
#     def clone(self):
#         raise TypeError(self.typename() + ' does not support cloning')
# 
#     def inline_copy(self):
#         import copy
#         return copy.copy(self)
# 
#     def write_out(self, out):
#         pass
# 
# Path: cmd_ir/nbt.py
# class NBTType(NativeType):
# 
#     __LOOKUP = {}
# 
#     def __init__(self, typename, compound=False):
#         self.name = typename
#         self._compound = compound
#         self.__LOOKUP[typename] = self
# 
#     @property
#     def exec_store_name(self):
#         assert self.isnumeric
#         # Currently we have the same names
#         return self.name
# 
#     @property
#     def isnumeric(self):
#         return not self._compound and self.name != 'string'
# 
#     def __str__(self):
#         return 'NBTType(%s)' % self.name
# 
#     def serialize(self):
#         return self.name
# 
#     @classmethod
#     def _init_from_parser(cls, value):
#         return cls.__LOOKUP[value]
# 
#     def new(self, *args):
#         # There are better ways of doing this
#         if self is self.byte:
#             impl = NBTByte
#         elif self is self.short:
#             impl = NBTShort
#         elif self is self.int:
#             impl = NBTInt
#         elif self is self.long:
#             impl = NBTLong
#         elif self is self.float:
#             impl = NBTFloat
#         elif self is self.double:
#             impl = NBTDouble
#         elif self is self.string:
#             impl = NBTString
#         elif self is self.list:
#             impl = NBTList
#         elif self is self.compound:
#             impl = NBTCompound
#         else:
#             assert False, str(self)
#         return impl(*args)
# 
#     byte = None
#     short = None
#     int = None
#     long = None
#     float = None
#     double = None
#     string = None
#     list = None
#     compound = None


import abc
import commands as c
        import copy
from .core_types import InsnArg, NativeType
from .nbt import NBTType
                      QConversions(10))


class OpenVar:

    def __init__(self, var, out, read=True, write=False):
        assert read or write
        self.var = var
        self.out = out
        self.write = write
        self.read = read
        self.ref = None
        self.using_temp = False

    def __enter__(self):
        self.ref = self.var._direct_ref()
        if self.ref is None:
            self.using_temp = True
            self.ref = self.out.allocate_temp()
            if self.read:
                self.var._write_to_reference(self.ref, self.out)
        return self.ref

    def __exit__(self, *args):
        # if not a direct reference, must write back
        if self.write and self.using_temp:
            self.var._read_from_reference(self.ref, self.out)
        if self.using_temp:
            self.out.free_temp(self.ref)


# Path: cmd_ir/core_types.py
# class InsnArg:
# 
#     @classmethod
#     def _init_from_parser(cls, value):
#         return value
# 
# class NativeType(InsnArg):
# 
#     @classmethod
#     def typename(cls):
#         return cls.__name__
# 
#     def clone(self):
#         raise TypeError(self.typename() + ' does not support cloning')
# 
#     def inline_copy(self):
#         import copy
#         return copy.copy(self)
# 
#     def write_out(self, out):
#         pass
# 
# Path: cmd_ir/nbt.py
# class NBTType(NativeType):
# 
#     __LOOKUP = {}
# 
#     def __init__(self, typename, compound=False):
#         self.name = typename
#         self._compound = compound
#         self.__LOOKUP[typename] = self
# 
#     @property
#     def exec_store_name(self):
#         assert self.isnumeric
#         # Currently we have the same names
#         return self.name
# 
#     @property
#     def isnumeric(self):
#         return not self._compound and self.name != 'string'
# 
#     def __str__(self):
#         return 'NBTType(%s)' % self.name
# 
#     def serialize(self):
#         return self.name
# 
#     @classmethod
#     def _init_from_parser(cls, value):
#         return cls.__LOOKUP[value]
# 
#     def new(self, *args):
#         # There are better ways of doing this
#         if self is self.byte:
#             impl = NBTByte
#         elif self is self.short:
#             impl = NBTShort
#         elif self is self.int:
#             impl = NBTInt
#         elif self is self.long:
#             impl = NBTLong
#         elif self is self.float:
#             impl = NBTFloat
#         elif self is self.double:
#             impl = NBTDouble
#         elif self is self.string:
#             impl = NBTString
#         elif self is self.list:
#             impl = NBTList
#         elif self is self.compound:
#             impl = NBTCompound
#         else:
#             assert False, str(self)
#         return impl(*args)
# 
#     byte = None
#     short = None
#     int = None
#     long = None
#     float = None
#     double = None
#     string = None
#     list = None
#     compound = None


# Path: cmd_ir/variables.py
import abc
import commands as c
        import copy
from .core_types import InsnArg, NativeType
from .nbt import NBTType

                      QConversions(10))


class OpenVar:

    def __init__(self, var, out, read=True, write=False):
        assert read or write
        self.var = var
        self.out = out
        self.write = write
        self.read = read
        self.ref = None
        self.using_temp = False

    def __enter__(self):
        self.ref = self.var._direct_ref()
        if self.ref is None:
            self.using_temp = True
            self.ref = self.out.allocate_temp()
            if self.read:
                self.var._write_to_reference(self.ref, self.out)
        return self.ref

    def __exit__(self, *args):
        # if not a direct reference, must write back
        if self.write and self.using_temp:
            self.var._read_from_reference(self.ref, self.out)
        if self.using_temp:
            self.out.free_temp(self.ref)


class Variable(NativeType, metaclass=abc.ABCMeta):