Example #1
0
    def convert_name_reference(self, ast_variable):
        """
        Converts a single name reference to a gsl processable format.
        :param ast_variable: a single variable
        :type ast_variable: ASTVariable
        :return: a gsl processable format of the variable
        :rtype: str
        """
        variable_name = NestNamesConverter.convert_to_cpp_name(
            ast_variable.get_name())
        symbol = ast_variable.get_scope().resolve_to_symbol(
            ast_variable.get_complete_name(), SymbolKind.VARIABLE)

        if PredefinedUnits.is_unit(ast_variable.get_complete_name()):
            return str(
                UnitConverter.get_factor(
                    PredefinedUnits.get_unit(
                        ast_variable.get_complete_name()).get_unit()))
        if symbol.is_init_values():
            return GSLNamesConverter.name(symbol)
        elif symbol.is_buffer():
            return 'node.B_.' + NestNamesConverter.buffer_value(symbol)
        elif variable_name == PredefinedVariables.E_CONSTANT:
            return 'numerics::e'
        elif symbol.is_local() or symbol.is_function:
            return variable_name
        elif symbol.has_vector_parameter():
            return 'node.get_' + variable_name + '()[i]'
        else:
            return 'node.get_' + variable_name + '()'
    def print_expression(self, node, prefix=''):
        """Print an expression.

        Parameters
        ----------
        node : ASTExpressionNode
            The expression node to print.
        prefix : str
            *See documentation for the function ExpressionsPrettyPrinter::print_function_call().*


        Returns
        -------
        s : str
            The expression string.
        """
        # todo : printing of literals etc. should be done by constant converter, not a type converter
        if isinstance(node, ASTSimpleExpression):
            if node.is_numeric_literal():
                return self.types_printer.pretty_print(
                    node.get_numeric_literal())
            elif node.is_variable() and node.get_scope() is not None:
                node_is_variable_symbol = node.get_scope().resolve_to_symbol(
                    node.variable.get_complete_name(),
                    SymbolKind.VARIABLE) is not None
                if not node_is_variable_symbol and PredefinedUnits.is_unit(
                        node.variable.get_complete_name()):
                    # case for a literal unit, e.g. "ms"
                    return str(
                        UnitConverter.get_factor(
                            PredefinedUnits.get_unit(
                                node.variable.get_complete_name()).get_unit()))

        return super(UnitlessExpressionPrinter,
                     self).print_expression(node, prefix=prefix)
Example #3
0
    def convert_name_reference(self,
                               ast_variable: ASTVariable,
                               prefix: str = ''):
        """
        Converts a single name reference to a gsl processable format.
        :param ast_variable: a single variable
        :type ast_variable: ASTVariable
        :return: a gsl processable format of the variable
        :rtype: str
        """
        variable_name = NestNamesConverter.convert_to_cpp_name(
            ast_variable.get_name())

        if variable_name == PredefinedVariables.E_CONSTANT:
            return 'numerics::e'

        symbol = ast_variable.get_scope().resolve_to_symbol(
            ast_variable.get_complete_name(), SymbolKind.VARIABLE)
        if symbol is None:
            # test if variable name can be resolved to a type
            if PredefinedUnits.is_unit(ast_variable.get_complete_name()):
                return str(
                    UnitConverter.get_factor(
                        PredefinedUnits.get_unit(
                            ast_variable.get_complete_name()).get_unit()))

            code, message = Messages.get_could_not_resolve(variable_name)
            Logger.log_message(
                log_level=LoggingLevel.ERROR,
                code=code,
                message=message,
                error_position=ast_variable.get_source_position())
            return ''

        if symbol.is_init_values():
            return GSLNamesConverter.name(symbol)

        if symbol.is_buffer():
            if isinstance(symbol.get_type_symbol(), UnitTypeSymbol):
                units_conversion_factor = UnitConverter.get_factor(
                    symbol.get_type_symbol().unit.unit)
            else:
                units_conversion_factor = 1
            s = ""
            if not units_conversion_factor == 1:
                s += "(" + str(units_conversion_factor) + " * "
            s += prefix + 'B_.' + NestNamesConverter.buffer_value(symbol)
            if symbol.has_vector_parameter():
                s += '[i]'
            if not units_conversion_factor == 1:
                s += ")"
            return s

        if symbol.is_local() or symbol.is_function:
            return variable_name

        if symbol.has_vector_parameter():
            return prefix + 'get_' + variable_name + '()[i]'

        return prefix + 'get_' + variable_name + '()'
 def setUp(self):
     Logger.init_logger(LoggingLevel.INFO)
     SymbolTable.initialize_symbol_table(ASTSourceLocation(start_line=0, start_column=0, end_line=0, end_column=0))
     PredefinedUnits.register_units()
     PredefinedTypes.register_types()
     PredefinedVariables.register_variables()
     PredefinedFunctions.register_functions()
Example #5
0
def handle_unit(unit_type):
    """
    Handles a handed over unit by creating the corresponding unit-type, storing it in the list of predefined
    units, creating a type symbol and returning it.
    :param unit_type: a single sympy unit symbol
    :type unit_type: Symbol (sympy)
    :return: a new type symbol
    :rtype: type_symbol
    """
    # first ensure that it does not already exists, if not create it and register it in the set of predefined units
    # first clean up the unit of not required components, here it is the 1.0 in front of the unit
    # e.g., 1.0 * 1 / ms. This step is not mandatory for correctness, but makes  reporting easier
    if isinstance(unit_type, units.Quantity) and unit_type.value == 1.0:
        to_process = unit_type.unit
    else:
        to_process = unit_type
    if str(to_process) not in PredefinedUnits.get_units().keys():
        unit_type_t = UnitType(name=str(to_process), unit=to_process)
        PredefinedUnits.register_unit(unit_type_t)
    # now create the corresponding type symbol if it does not exists
    if PredefinedTypes.get_type(str(to_process)) is None:
        type_symbol = UnitTypeSymbol(
            unit=PredefinedUnits.get_unit(str(to_process)))
        PredefinedTypes.register_type(type_symbol)
    return PredefinedTypes.get_type(name=str(to_process))
    def convert_name_reference(self, ast_variable):
        """
        Converts a single name reference to a gsl processable format.
        :param ast_variable: a single variable
        :type ast_variable: ASTVariable
        :return: a gsl processable format of the variable
        :rtype: str
        """
        variable_name = NestNamesConverter.convert_to_cpp_name(ast_variable.get_name())
        symbol = ast_variable.get_scope().resolve_to_symbol(ast_variable.get_complete_name(), SymbolKind.VARIABLE)

        if PredefinedUnits.is_unit(ast_variable.get_complete_name()):
            return str(
                UnitConverter.get_factor(PredefinedUnits.get_unit(ast_variable.get_complete_name()).get_unit()))
        if symbol.is_init_values():
            return GSLNamesConverter.name(symbol)
        elif symbol.is_buffer():
            return 'node.B_.' + NestNamesConverter.buffer_value(symbol)
        elif variable_name == PredefinedVariables.E_CONSTANT:
            return 'numerics::e'
        elif symbol.is_local() or symbol.is_function:
            return variable_name
        elif symbol.has_vector_parameter():
            return 'node.get_' + variable_name + '()[i]'
        else:
            return 'node.get_' + variable_name + '()'
    def convert_name_reference(self, variable):
        """
        Converts a single variable to nest processable format.
        :param variable: a single variable.
        :type variable: ASTVariable
        :return: a nest processable format.
        :rtype: str
        """
        from pynestml.codegeneration.nest_printer import NestPrinter
        assert (variable is not None and isinstance(variable, ASTVariable)), \
            '(PyNestML.CodeGeneration.NestReferenceConverter) No or wrong type of uses-gsl provided (%s)!' % type(
                variable)
        variable_name = NestNamesConverter.convert_to_cpp_name(
            variable.get_complete_name())

        if variable_name == PredefinedVariables.E_CONSTANT:
            return 'numerics::e'
        else:
            symbol = variable.get_scope().resolve_to_symbol(
                variable_name, SymbolKind.VARIABLE)
            if symbol is None:
                # test if variable name can be resolved to a type
                if PredefinedUnits.is_unit(variable.get_complete_name()):
                    return str(
                        UnitConverter.get_factor(
                            PredefinedUnits.get_unit(
                                variable.get_complete_name()).get_unit()))

                code, message = Messages.get_could_not_resolve(variable_name)
                Logger.log_message(
                    log_level=LoggingLevel.ERROR,
                    code=code,
                    message=message,
                    error_position=variable.get_source_position())
                return ''
            else:
                if symbol.is_local():
                    return variable_name + (
                        '[i]' if symbol.has_vector_parameter() else '')
                elif symbol.is_buffer():
                    return NestPrinter.print_origin(symbol) + NestNamesConverter.buffer_value(symbol) \
                           + ('[i]' if symbol.has_vector_parameter() else '')
                else:
                    if symbol.is_function:
                        return 'get_' + variable_name + '()' + (
                            '[i]' if symbol.has_vector_parameter() else '')
                    else:
                        if symbol.is_init_values():
                            temp = NestPrinter.print_origin(symbol)
                            if self.uses_gsl:
                                temp += GSLNamesConverter.name(symbol)
                            else:
                                temp += NestNamesConverter.name(symbol)
                            temp += ('[i]'
                                     if symbol.has_vector_parameter() else '')
                            return temp
                        else:
                            return NestPrinter.print_origin(symbol) + \
                                   NestNamesConverter.name(symbol) + \
                                   ('[i]' if symbol.has_vector_parameter() else '')
    def setUp(self):
        PredefinedUnits.register_units()
        PredefinedTypes.register_types()
        PredefinedFunctions.register_functions()
        PredefinedVariables.register_variables()
        SymbolTable.initialize_symbol_table(ASTSourceLocation(start_line=0, start_column=0, end_line=0, end_column=0))
        Logger.init_logger(LoggingLevel.INFO)

        self.target_path = str(os.path.realpath(os.path.join(os.path.dirname(__file__), os.path.join(
            os.pardir, 'target'))))
Example #9
0
    def setUp(self) -> None:
        PredefinedUnits.register_units()
        PredefinedTypes.register_types()
        PredefinedFunctions.register_functions()
        PredefinedVariables.register_variables()
        SymbolTable.initialize_symbol_table(ASTSourceLocation(start_line=0, start_column=0, end_line=0, end_column=0))
        Logger.init_logger(LoggingLevel.INFO)

        self.target_path = str(os.path.realpath(os.path.join(os.path.dirname(__file__),
                                                             os.path.join(os.pardir, 'target'))))
Example #10
0
 def register_unit(cls, unit):
     """
     Registers a new astropy unit into the system
     :param unit: an astropy Unit object
     :type unit: astropy.units.core.Unit
     """
     unit_type = UnitType(str(unit), unit)
     PredefinedUnits.register_unit(unit_type)
     type_symbol = UnitTypeSymbol(unit=unit_type)
     cls.register_type(type_symbol)
     return
Example #11
0
 def register_unit(cls, unit):
     """
     Registers a new astropy unit into the system
     :param unit: an astropy Unit object
     :type unit: astropy.units.core.Unit
     """
     unit_type = UnitType(str(unit), unit)
     PredefinedUnits.register_unit(unit_type)
     type_symbol = UnitTypeSymbol(unit=unit_type)
     cls.register_type(type_symbol)
     return
Example #12
0
 def register_unit(cls, unit):
     """
     Registers a new sympy unit into the system
     :param unit: a sympy unit.
     :type unit: SympyUnit
     """
     unit_type = UnitType(str(unit), unit)
     PredefinedUnits.register_unit(unit_type)
     type_symbol = UnitTypeSymbol(unit=unit_type)
     cls.register_type(type_symbol)
     return
    def convert_name_reference(self, variable):
        """
        Converts a single variable to nest processable format.
        :param variable: a single variable.
        :type variable: ASTVariable
        :return: a nest processable format.
        :rtype: str
        """
        from pynestml.codegeneration.nest_printer import NestPrinter
        assert (variable is not None and isinstance(variable, ASTVariable)), \
            '(PyNestML.CodeGeneration.NestReferenceConverter) No or wrong type of uses-gsl provided (%s)!' % type(
                variable)
        variable_name = NestNamesConverter.convert_to_cpp_name(variable.get_complete_name())

        if PredefinedUnits.is_unit(variable.get_complete_name()):
            return str(
                UnitConverter.get_factor(PredefinedUnits.get_unit(variable.get_complete_name()).get_unit()))
        if variable_name == PredefinedVariables.E_CONSTANT:
            return 'numerics::e'
        else:
            symbol = variable.get_scope().resolve_to_symbol(variable_name, SymbolKind.VARIABLE)
            if symbol is None:
                # this should actually not happen, but an error message is better than an exception
                code, message = Messages.get_could_not_resolve(variable_name)
                Logger.log_message(log_level=LoggingLevel.ERROR, code=code, message=message,
                                   error_position=variable.get_source_position())
                return ''
            else:
                if symbol.is_local():
                    return variable_name + ('[i]' if symbol.has_vector_parameter() else '')
                elif symbol.is_buffer():
                    return NestPrinter.print_origin(symbol) + NestNamesConverter.buffer_value(symbol) \
                           + ('[i]' if symbol.has_vector_parameter() else '')
                else:
                    if symbol.is_function:
                        return 'get_' + variable_name + '()' + ('[i]' if symbol.has_vector_parameter() else '')
                    else:
                        if symbol.is_init_values():
                            temp = NestPrinter.print_origin(symbol)
                            if self.uses_gsl:
                                temp += GSLNamesConverter.name(symbol)
                            else:
                                temp += NestNamesConverter.name(symbol)
                            temp += ('[i]' if symbol.has_vector_parameter() else '')
                            return temp
                        else:
                            return NestPrinter.print_origin(symbol) + \
                                   NestNamesConverter.name(symbol) + \
                                   ('[i]' if symbol.has_vector_parameter() else '')
Example #14
0
 def __register_units(cls):
     """
     Adds all units as predefined type symbols to the list of available types.
     """
     from pynestml.symbols.predefined_units import PredefinedUnits
     from pynestml.symbols.unit_type_symbol import UnitTypeSymbol
     units = PredefinedUnits.get_units()
     for unitName in units.keys():
         type_symbol = UnitTypeSymbol(unit=units[unitName])
         cls.name2type[unitName] = type_symbol
     return
Example #15
0
 def __register_units(cls):
     """
     Adds all units as predefined type symbols to the list of available types.
     """
     from pynestml.symbols.predefined_units import PredefinedUnits
     from pynestml.symbols.unit_type_symbol import UnitTypeSymbol
     units = PredefinedUnits.get_units()
     for unitName in units.keys():
         type_symbol = UnitTypeSymbol(unit=units[unitName])
         cls.name2type[unitName] = type_symbol
     return
Example #16
0
    def is_conductance_based(self) -> bool:
        """
        Indicates whether this element is conductance based, based on the physical units of the spike input port. If the unit can be cast to Siemens, the function returns True, otherwise it returns False.

        :return: True if conductance based, otherwise False.
        """
        is_cond_based = self.type_symbol.is_castable_to(
            UnitTypeSymbol(unit=PredefinedUnits.get_unit("S")))
        is_curr_based = self.type_symbol.is_castable_to(
            UnitTypeSymbol(unit=PredefinedUnits.get_unit("A")))
        if is_cond_based == is_curr_based:
            code, message = Messages.get_could_not_determine_cond_based(
                type_str=self.type_symbol.print_nestml_type(), name=self.name)
            Logger.log_message(
                node=None,
                code=code,
                message=message,
                log_level=LoggingLevel.WARNING,
                error_position=ASTSourceLocation.get_added_source_position())
            return False

        return is_cond_based
def handle_unit(unit_type):
    """
    Handles a handed over unit by creating the corresponding unit-type, storing it in the list of predefined
    units, creating a type symbol and returning it.
    :param unit_type: astropy unit object
    :type unit_type: astropy.units.core.Unit
    :return: a new type symbol
    :rtype: TypeSymbol
    """
    # first ensure that it does not already exists, if not create it and register it in the set of predefined units
    # first clean up the unit of not required components, here it is the 1.0 in front of the unit
    # e.g., 1.0 * 1 / ms. This step is not mandatory for correctness, but makes  reporting easier
    if isinstance(unit_type, units.Quantity) and unit_type.value == 1.0:
        to_process = unit_type.unit
    else:
        to_process = unit_type
    if str(to_process) not in PredefinedUnits.get_units().keys():
        unit_type_t = UnitType(name=str(to_process), unit=to_process)
        PredefinedUnits.register_unit(unit_type_t)
    # now create the corresponding type symbol if it does not exists
    if PredefinedTypes.get_type(str(to_process)) is None:
        type_symbol = UnitTypeSymbol(unit=PredefinedUnits.get_unit(str(to_process)))
        PredefinedTypes.register_type(type_symbol)
    return PredefinedTypes.get_type(name=str(to_process))
Example #18
0
from antlr4 import *

from pynestml.meta_model.ast_nestml_compilation_unit import ASTNestMLCompilationUnit
from pynestml.utils.ast_source_location import ASTSourceLocation
from pynestml.generated.PyNestMLLexer import PyNestMLLexer
from pynestml.generated.PyNestMLParser import PyNestMLParser
from pynestml.symbol_table.symbol_table import SymbolTable
from pynestml.symbols.predefined_functions import PredefinedFunctions
from pynestml.symbols.predefined_types import PredefinedTypes
from pynestml.symbols.predefined_units import PredefinedUnits
from pynestml.symbols.predefined_variables import PredefinedVariables
from pynestml.utils.logger import LoggingLevel, Logger
from pynestml.visitors.ast_builder_visitor import ASTBuilderVisitor

# setups the infrastructure
PredefinedUnits.register_units()
PredefinedTypes.register_types()
PredefinedFunctions.register_functions()
PredefinedVariables.register_variables()
SymbolTable.initialize_symbol_table(
    ASTSourceLocation(start_line=0, start_column=0, end_line=0, end_column=0))
Logger.init_logger(LoggingLevel.INFO)


class ASTBuildingTest(unittest.TestCase):
    def test(self):
        for filename in os.listdir(
                os.path.realpath(
                    os.path.join(os.path.dirname(__file__),
                                 os.path.join('..', 'models')))):
            if filename.endswith(".nestml"):
Example #19
0
def init_predefined():
    # initialize the predefined elements
    PredefinedUnits.register_units()
    PredefinedTypes.register_types()
    PredefinedFunctions.register_functions()
    PredefinedVariables.register_variables()
Example #20
0
# along with NEST.  If not, see <http://www.gnu.org/licenses/>.

import unittest

from pynestml.meta_model.ast_source_location import ASTSourceLocation
from pynestml.symbol_table.symbol_table import SymbolTable
from pynestml.symbols.predefined_functions import PredefinedFunctions
from pynestml.symbols.predefined_types import PredefinedTypes
from pynestml.symbols.predefined_units import PredefinedUnits
from pynestml.symbols.predefined_variables import PredefinedVariables
from pynestml.utils.ast_nestml_printer import ASTNestMLPrinter
from pynestml.utils.logger import LoggingLevel, Logger
from pynestml.utils.model_parser import ModelParser

# setups the infrastructure
PredefinedUnits.register_units()
PredefinedTypes.register_types()
PredefinedFunctions.register_functions()
PredefinedVariables.register_variables()
SymbolTable.initialize_symbol_table(ASTSourceLocation(start_line=0, start_column=0, end_line=0, end_column=0))
Logger.init_logger(LoggingLevel.INFO)


class NestMLPrinterTest(unittest.TestCase):
    """
    Tests if the NestML printer works as intended.
    """

    def test_block_with_variables_with_comments(self):
        block = '\n' \
                '/* pre1\n' \
Example #21
0
    def convert_name_reference(self, variable: ASTVariable, prefix='') -> str:
        """
        Converts a single variable to nest processable format.
        :param variable: a single variable.
        :type variable: ASTVariable
        :return: a nest processable format.
        """
        from pynestml.codegeneration.nest_printer import NestPrinter

        if isinstance(variable, ASTExternalVariable):
            _name = str(variable)
            if variable.get_alternate_name():
                # the disadvantage of this approach is that the time the value is to be obtained is not explicitly specified, so we will actually get the value at the end of the min_delay timestep
                return "((POST_NEURON_TYPE*)(__target))->get_" + variable.get_alternate_name(
                ) + "()"

            return "((POST_NEURON_TYPE*)(__target))->get_" + _name + "(_tr_t)"

        if variable.get_name() == PredefinedVariables.E_CONSTANT:
            return 'numerics::e'

        symbol = variable.get_scope().resolve_to_symbol(
            variable.get_complete_name(), SymbolKind.VARIABLE)
        if symbol is None:
            # test if variable name can be resolved to a type
            if PredefinedUnits.is_unit(variable.get_complete_name()):
                return str(
                    UnitConverter.get_factor(
                        PredefinedUnits.get_unit(
                            variable.get_complete_name()).get_unit()))

            code, message = Messages.get_could_not_resolve(variable.get_name())
            Logger.log_message(log_level=LoggingLevel.ERROR,
                               code=code,
                               message=message,
                               error_position=variable.get_source_position())
            return ''

        if symbol.is_local():
            return variable.get_name() + (
                '[' + variable.get_vector_parameter() +
                ']' if symbol.has_vector_parameter() else '')
        if symbol.is_buffer():
            if isinstance(symbol.get_type_symbol(), UnitTypeSymbol):
                units_conversion_factor = UnitConverter.get_factor(
                    symbol.get_type_symbol().unit.unit)
            else:
                units_conversion_factor = 1
            s = ""
            if not units_conversion_factor == 1:
                s += "(" + str(units_conversion_factor) + " * "
            s += NestPrinter.print_origin(
                symbol,
                prefix=prefix) + NestNamesConverter.buffer_value(symbol)
            if symbol.has_vector_parameter():
                s += '[' + variable.get_vector_parameter() + ']'
            if not units_conversion_factor == 1:
                s += ")"
            return s

        if symbol.is_inline_expression:
            return 'get_' + variable.get_name() + '()' + (
                '[i]' if symbol.has_vector_parameter() else '')

        if symbol.is_kernel():
            assert False, "NEST reference converter cannot print kernel; kernel should have been converted during code generation"

        if symbol.is_state():
            temp = ""
            temp += NestNamesConverter.getter(symbol) + "()"
            temp += ('[' + variable.get_vector_parameter() +
                     ']' if symbol.has_vector_parameter() else '')
            return temp

        variable_name = NestNamesConverter.convert_to_cpp_name(
            variable.get_complete_name())
        if symbol.is_local():
            return variable_name + ('[i]'
                                    if symbol.has_vector_parameter() else '')

        if symbol.is_inline_expression:
            return 'get_' + variable_name + '()' + (
                '[i]' if symbol.has_vector_parameter() else '')

        return NestPrinter.print_origin(symbol, prefix=prefix) + \
            NestNamesConverter.name(symbol) + \
            ('[' + variable.get_vector_parameter() + ']' if symbol.has_vector_parameter() else '')
    def convert_name_reference(self, ast_variable):
        """
        Convert name reference.

        :param ast_variable: a single variable
        :type ast_variable: ASTVariable
        :return: pretty-printed format string
        :rtype: str
        """
        var_name = ast_variable.get_name()
        var_complete_name = ast_variable.get_complete_name()
        if not ast_variable.get_scope().resolve_to_symbol(var_complete_name, SymbolKind.VARIABLE) \
                and PredefinedUnits.is_unit(var_complete_name):
            # convert a unit (e.g. ms, pA)
            # var_name = "\color{grey}\mathrm{" + var_name + "}\color{black}"	# readthedocs does not support \color!
            var_name = r"\mathrm{" + var_name + "}"
        # convert first underscore
        usc_idx = var_name.find("_")
        if usc_idx > 0:
            var_name = var_name[:usc_idx] + "_{" + var_name[
                usc_idx + 1:].replace(
                    "_",
                    ",") + "}" + "'" * ast_variable.get_differential_order()
        symbols = {
            "inf": r"\\infty",
            "alpha": r"\\alpha",
            "beta": r"\\beta",
            "gamma": r"\\gamma",
            "delta": r"\\delta",
            "epsilon": r"\\epsilon",
            "zeta": r"\\zeta",
            "eta": r"\\eta",
            "theta": r"\\theta",
            "iota": r"\\iota",
            "kappa": r"\\kappa",
            "lambda": r"\\lambda",
            "labda": r"\\lambda",
            "mu": r"\\mu",
            "nu": r"\\nu",
            "xi": r"\\xi",
            "omnikron": "o",
            "pi": r"\\pi",
            "rho": r"\\rho",
            "sigma": r"\\sigma",
            "tau": r"\\tau",
            "upsilon": r"\\upsilon",
            "phi": r"\\phi",
            "chi": r"\\chi",
            "psi": r"\\psi",
            "omega": r"\\omega",
            "Alpha": r"\\Alpha",
            "Beta": r"\\Beta",
            "Gamma": r"\\Gamma",
            "Delta": r"\\Delta",
            "Epsilon": r"\\Epsilon",
            "Zeta": r"\\zeta",
            "Eta": r"\\Eta",
            "Theta": r"\\Theta",
            "Iota": r"\\Iota",
            "Kappa": r"\\Kappa",
            "Lambda": r"\\Lambda",
            "Labda": r"\\Lambda",
            "Mu": r"\\Mu",
            "Nu": r"\\Nu",
            "Xi": r"\\Xi",
            "Omnikron": "O",
            "Pi": r"\\Pi",
            "Rho": r"\\Rho",
            "Sigma": r"\\Sigma",
            "Tau": r"\\Tau",
            "Upsilon": r"\\Upsilon",
            "Phi": r"\\Phi",
            "Chi": r"\\Chi",
            "Psi": r"\\Psi",
            "Omega": r"\\Omega"
        }
        for symbol_find, symbol_replace in symbols.items():
            before = var_name
            var_name = re.sub(r"(?<![a-zA-Z])(" + symbol_find +
                              ")(?![a-zA-Z])", symbol_replace,
                              var_name)  # "whole word" match
            after = var_name
        return var_name
    def convert_name_reference(self, variable, prefix='', with_origins = True):
        """
        Converts a single variable to nest processable format.
        :param variable: a single variable.
        :type variable: ASTVariable
        :return: a nest processable format.
        :rtype: str
        """
        from pynestml.codegeneration.nest_printer import NestPrinter
        assert (variable is not None and isinstance(variable, ASTVariable)), \
            '(PyNestML.CodeGeneration.NestReferenceConverter) No or wrong type of uses-gsl provided (%s)!' % type(
                variable)
        variable_name = NestNamesConverter.convert_to_cpp_name(variable.get_complete_name())

        if variable_name == PredefinedVariables.E_CONSTANT:
            return 'numerics::e'

        assert variable.get_scope() is not None, "Undeclared variable: " + variable.get_complete_name()

        symbol = variable.get_scope().resolve_to_symbol(variable_name, SymbolKind.VARIABLE)
        if symbol is None:
            # test if variable name can be resolved to a type
            if PredefinedUnits.is_unit(variable.get_complete_name()):
                return str(UnitConverter.get_factor(PredefinedUnits.get_unit(variable.get_complete_name()).get_unit()))

            code, message = Messages.get_could_not_resolve(variable_name)
            Logger.log_message(log_level=LoggingLevel.ERROR, code=code, message=message,
                               error_position=variable.get_source_position())
            return ''

        if symbol.is_local():
            return variable_name + ('[i]' if symbol.has_vector_parameter() else '')

        if symbol.is_buffer():
            if isinstance(symbol.get_type_symbol(), UnitTypeSymbol):
                units_conversion_factor = UnitConverter.get_factor(symbol.get_type_symbol().unit.unit)
            else:
                units_conversion_factor = 1
            s = ""
            if not units_conversion_factor == 1:
                s += "(" + str(units_conversion_factor) + " * "
            s += NestPrinter.print_origin(symbol, prefix=prefix) if with_origins else ''
            s += NestNamesConverter.buffer_value(symbol)
            if symbol.has_vector_parameter():
                s += '[i]'
            if not units_conversion_factor == 1:
                s += ")"
            return s

        if symbol.is_inline_expression:
            return 'get_' + variable_name + '()' + ('[i]' if symbol.has_vector_parameter() else '')

        if symbol.is_kernel():
            assert False, "NEST reference converter cannot print kernel; kernel should have been converted during code generation"

        if symbol.is_state():
            temp = NestPrinter.print_origin(symbol, prefix=prefix) if with_origins else ''
            if self.uses_gsl:
                temp += GSLNamesConverter.name(symbol)
            else:
                temp += NestNamesConverter.name(symbol)
            temp += ('[i]' if symbol.has_vector_parameter() else '')
            return temp

        return (NestPrinter.print_origin(symbol, prefix=prefix) if with_origins else '') + \
            NestNamesConverter.name(symbol) + \
            ('[i]' if symbol.has_vector_parameter() else '')