1 // Copyright 2004-2008 Castle Project - http://www.castleproject.org/
3 // Licensed under the Apache License, Version 2.0 (the "License");
4 // you may not use this file except in compliance with the License.
5 // You may obtain a copy of the License at
7 // http://www.apache.org/licenses/LICENSE-2.0
9 // Unless required by applicable law or agreed to in writing, software
10 // distributed under the License is distributed on an "AS IS" BASIS,
11 // WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
12 // See the License for the specific language governing permissions and
13 // limitations under the License.
15 namespace Castle
.Rook
.Compiler
.AST
18 using System
.Collections
;
19 using System
.Collections
.Specialized
;
22 public sealed class SymbolTable
: ISymbolTable
24 private readonly ISymbolTable parent
;
26 private ScopeType scopeType
;
28 private IDictionary identifierMap
= new HybridDictionary();
29 private IDictionary methodMap
= new HybridDictionary();
36 public SymbolTable(ISymbolTable parent
, ScopeType scopeType
)
39 this.scopeType
= scopeType
;
42 public bool IsDefined(String name
)
44 if (name
== null) throw new ArgumentNullException("name");
46 return IsIdentifierDefined(name
) || IsMethodDefined(name
);
49 public bool IsDefinedRecursive(String name
)
51 if (name
== null) throw new ArgumentNullException("name");
53 return (!IsDefined(name
) && parent
!= null) ?
54 parent
.IsDefinedRecursive(name
) : false;
57 public void AddMethod(MethodDefinitionStatement methodDef
)
59 if (methodDef
== null) throw new ArgumentNullException("methodDef");
61 String name
= methodDef
.Name
;
65 if (!methodMap
.Contains(name
))
67 list
= new ArrayList();
68 methodMap
[name
] = list
;
72 list
= (IList
) methodMap
[name
];
78 public void AddIdentifier(Identifier identifier
)
80 if (identifier
== null) throw new ArgumentNullException("identifier");
82 String name
= identifier
.Name
;
84 if (name
== null) throw new ArgumentNullException("identifier.name");
86 if (identifierMap
.Contains(name
))
88 throw new Exception(name
+ " is already defined within this scope");
91 identifierMap
[name
] = identifier
;
94 public Identifier
GetIdentifier(String name
)
96 if (IsIdentifierDefined(name
))
98 return (Identifier
) identifierMap
[name
];
101 throw new Exception(name
+ " is not defined on this scope");
104 public MethodDefinitionStatement
GetMethod(String name
)
106 if (name
== null) throw new ArgumentNullException("name");
108 if (IsMethodDefined(name
))
110 IList list
= (IList
) methodMap
[name
];
111 return list
[0] as MethodDefinitionStatement
;
114 throw new Exception(name
+ " is not defined on this scope");
117 public MethodDefinitionStatement
[] GetMethods(String name
)
119 if (name
== null) throw new ArgumentNullException("name");
121 if (IsMethodDefined(name
))
123 IList list
= (IList
) methodMap
[name
];
124 Array array
= Array
.CreateInstance( typeof(MethodDefinitionStatement
), list
.Count
);
125 list
.CopyTo( array
, 0 );
126 return (MethodDefinitionStatement
[]) array
;
129 throw new Exception(name
+ " is not defined on this scope");
132 public ISymbolTable Parent
134 get { return parent; }
137 public ScopeType ScopeType
139 get { return scopeType; }
142 private bool IsIdentifierDefined(String name
)
144 return identifierMap
.Contains(name
);
147 private bool IsMethodDefined(String name
)
149 return methodMap
.Contains(name
);