76 lines
2.1 KiB
C#
76 lines
2.1 KiB
C#
using System;
|
|
using System.Collections.Generic;
|
|
using Upsilon.Binder.VariableSymbols;
|
|
using Type = Upsilon.BaseTypes.Type;
|
|
|
|
namespace Upsilon.Binder
|
|
{
|
|
public class BoundScope : IDisposable
|
|
{
|
|
public readonly BoundScope ParentScope;
|
|
public BoundScope ReadOnlyScope { get; private set; }
|
|
public readonly Dictionary<string, VariableSymbol> Variables;
|
|
public Type ReturnType { get; set; } = Type.Nil;
|
|
|
|
public BoundScope(BoundScope parentScope)
|
|
{
|
|
ParentScope = parentScope;
|
|
Variables = new Dictionary<string, VariableSymbol>();
|
|
}
|
|
public BoundScope(Dictionary<string, VariableSymbol> variables, BoundScope parentScope)
|
|
{
|
|
ParentScope = parentScope;
|
|
Variables = variables;
|
|
}
|
|
|
|
public static BoundScope WithReadOnlyScope(BoundScope readOnlyScope)
|
|
{
|
|
var scope = new BoundScope(null) {ReadOnlyScope = readOnlyScope};
|
|
return scope;
|
|
}
|
|
|
|
public void Dispose()
|
|
{
|
|
//Variables.Clear();
|
|
}
|
|
|
|
public void DefineLocalVariable(VariableSymbol var)
|
|
{
|
|
Variables.Add(var.Name, var);
|
|
}
|
|
|
|
public void AssignToNearest(VariableSymbol var)
|
|
{
|
|
if (Variables.ContainsKey(var.Name))
|
|
{
|
|
|
|
}
|
|
else if (ParentScope != null)
|
|
{
|
|
ParentScope.AssignToNearest(var);
|
|
}
|
|
else
|
|
{
|
|
Variables.Add(var.Name, var);
|
|
}
|
|
}
|
|
|
|
public bool TryGetVariable(string key, bool allowUpperScopes, out VariableSymbol result)
|
|
{
|
|
if (Variables.TryGetValue(key, out result))
|
|
{
|
|
return true;
|
|
}
|
|
if (ParentScope != null && allowUpperScopes)
|
|
{
|
|
return ParentScope.TryGetVariable(key, true, out result);
|
|
}
|
|
if (ReadOnlyScope != null && allowUpperScopes)
|
|
{
|
|
return ReadOnlyScope.TryGetVariable(key, true, out result);
|
|
}
|
|
return false;
|
|
}
|
|
|
|
}
|
|
} |