1 # This file is part of NIT ( http://www.nitlanguage.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.
21 # A member or an inner class.
22 abstract class MemberOrInner
25 # The type of the introducer.
26 type INTRODUCER_TYPE: MemberIntroducer
28 # The node used to represent the `MProperty` node.
30 # Only defined if `self` is at the root of a reimplementation graph, and
31 # only once `put_in_graph` is called.
32 var introducer
: nullable INTRODUCER_TYPE = null
36 self.labels
.add
("MPropDef")
39 # Does this member introduce the property?
40 fun is_intro
: Bool is abstract
42 redef fun put_in_graph
do
44 self["is_intro"] = is_intro
46 var visibility
= self["visibility"]
47 var name
= self["name"]
49 introducer
= create_introducer
50 if name
isa String then
51 introducer
.name
= name
53 if visibility
isa String then
54 introducer
.visibility
= visibility
56 introducer
.put_in_graph
60 redef fun put_edges
do
62 var intro
= resolve_introducer
65 graph
.add_edge
(self, "DEFINES", intro
)
69 fun visibility
=(visibility
: String) do
70 self["visibility"] = visibility
71 if introducer
!= null then
72 introducer
.as(not null).visibility
= visibility
78 # Return `""` by default.
79 fun visibility
: String do
80 var visibility
= self["visibility"]
81 if visibility
isa String then return visibility
85 redef fun name
=(name
: String) do
87 if introducer
!= null then
88 introducer
.as(not null).name
= name
92 # Create an instance of `MemberIntroducer` that will be linked to `self`.
93 protected fun create_introducer
: INTRODUCER_TYPE is abstract
95 # Find the nearest reimplementation root.
96 fun resolve_introducer
: nullable INTRODUCER_TYPE is abstract
100 abstract class Member
103 # Members that this member redefines/reimplements.
104 var reimplemented
: SimpleCollection[String] = new Array[String]
106 # Set the static type.
107 fun static_type
=(static_type
: nullable TypeEntity) is abstract
109 # Get the static type.
110 fun static_type
: nullable TypeEntity is abstract
112 # Append the specified parameter to the signature.
113 fun add_parameter
(parameter
: MemberParameter) do end
115 # Append a member that is reimplemeneted by `self`.
116 fun reimplement
(parent
: String) do
117 reimplemented
.add
(parent
)
120 redef fun is_intro
do return reimplemented
.length
<= 0
122 # Is the member abstract?
123 fun is_abstract
=(is_abstract
: Bool) do
124 self["is_abstract"] = is_abstract
127 # Find the nearest reimplementation root.
129 # var g = new ProjectGraph("foo")
130 # var m1 = new Attribute(g)
131 # var m2 = new Attribute(g)
132 # var m3 = new Attribute(g)
136 # m2.reimplement("1")
138 # assert m1.resolve_introducer == m1.introducer
139 # assert m2.resolve_introducer == m1.introducer
142 # m3.reimplement("3")
144 # assert m3.resolve_introducer == null
145 redef fun resolve_introducer
do
146 if introducer
== null then
147 var member_queue
= new List[String]
148 var visited
= new HashSet[Member]
151 member_queue
.add_all
(reimplemented
)
152 while not member_queue
.is_empty
do
153 member
= graph
.by_id
[member_queue
.shift
].as(Member)
154 if visited
.has
(member
) then
156 else if member
.is_intro
then
157 return member
.introducer
160 member_queue
.add_all
(member
.reimplemented
)
170 # An unrecognized member.
172 # Used to simplify the handling of ignored entities.
176 redef fun put_in_graph
do end
177 redef fun put_edges
do end
180 # A local definition of a method.
184 redef type INTRODUCER_TYPE: MethodIntroducer
186 # The method’s signature.
187 var signature
: Signature is noinit
, writable
191 self.labels
.add
("MMethodDef")
192 self["is_intern"] = false # TODO
193 self["is_extern"] = false # TODO
194 signature
= new Signature(graph
)
198 # Set the return type.
199 redef fun static_type
=(static_type
: nullable TypeEntity) do
200 signature
.return_type
= static_type
203 # Get the return type.
204 redef fun static_type
: nullable TypeEntity do return signature
.return_type
206 redef fun add_parameter
(parameter
: MemberParameter) do
207 signature
.parameters
.add
(parameter
)
210 redef fun create_introducer
do return new MethodIntroducer(graph
)
212 redef fun put_in_graph
do
214 signature
.put_in_graph
217 redef fun put_edges
do
219 graph
.add_edge
(self, "SIGNATURE", signature
)
223 # A local definition of an attribute.
227 redef type INTRODUCER_TYPE: AttributeIntroducer
230 redef var static_type
: nullable TypeEntity = null is writable
234 self.labels
.add
("MAttributeDef")
237 redef fun create_introducer
do return new AttributeIntroducer(graph
)
239 redef fun put_in_graph
do
241 if static_type
!= null then
242 static_type
.as(not null).put_in_graph
246 redef fun put_edges
do
248 if static_type
!= null then
249 graph
.add_edge
(self, "TYPE", static_type
.as(not null))
254 # The `MProperty` node of a root of a reimplementation graph.
255 abstract class MemberIntroducer
260 self.labels
.add
("MProperty")
261 self["visibility"] = "public"
264 # Set the visibility.
265 fun visibility
=(visibility
: String) do
266 self["visibility"] = visibility
269 # Get the visibility.
271 # Return `""` by default.
272 fun visibility
: String do
273 var visibility
= self["visibility"]
274 if visibility
isa String then return visibility
279 # A `MProperty` node for a method.
280 class MethodIntroducer
281 super MemberIntroducer
285 self.labels
.add
("MMethod")
286 self["is_init"] = false # TODO
290 # A `MProperty` node for an attribute.
291 class AttributeIntroducer
292 super MemberIntroducer
296 self.labels
.add
("MAttribute")
301 # Append the specified member.
302 fun declare_member
(member
: Member) do end