Mercurial > hg > graal-compiler
comparison graal/com.oracle.truffle.sl/src/com/oracle/truffle/sl/nodes/access/SLReadPropertyCacheNode.java @ 18412:997bc9764a9a
SL: use the truffle object storage model to represent SL objects
author | Andreas Woess <andreas.woess@jku.at> |
---|---|
date | Tue, 18 Nov 2014 12:08:51 +0100 |
parents | |
children | ccb97347d874 |
comparison
equal
deleted
inserted
replaced
18411:dc2e000bed40 | 18412:997bc9764a9a |
---|---|
1 /* | |
2 * Copyright (c) 2013, 2014, Oracle and/or its affiliates. All rights reserved. | |
3 * DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER. | |
4 * | |
5 * This code is free software; you can redistribute it and/or modify it | |
6 * under the terms of the GNU General Public License version 2 only, as | |
7 * published by the Free Software Foundation. | |
8 * | |
9 * This code is distributed in the hope that it will be useful, but WITHOUT | |
10 * ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or | |
11 * FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License | |
12 * version 2 for more details (a copy is included in the LICENSE file that | |
13 * accompanied this code). | |
14 * | |
15 * You should have received a copy of the GNU General Public License version | |
16 * 2 along with this work; if not, write to the Free Software Foundation, | |
17 * Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA. | |
18 * | |
19 * Please contact Oracle, 500 Oracle Parkway, Redwood Shores, CA 94065 USA | |
20 * or visit www.oracle.com if you need additional information or have any | |
21 * questions. | |
22 */ | |
23 package com.oracle.truffle.sl.nodes.access; | |
24 | |
25 import com.oracle.truffle.api.*; | |
26 import com.oracle.truffle.api.nodes.*; | |
27 import com.oracle.truffle.api.object.*; | |
28 import com.oracle.truffle.sl.nodes.*; | |
29 import com.oracle.truffle.sl.runtime.*; | |
30 | |
31 /** | |
32 * The node for accessing a property of an object. When executed, this node first evaluates the | |
33 * object expression on the left side of the dot operator and then reads the named property. | |
34 */ | |
35 public abstract class SLReadPropertyCacheNode extends Node { | |
36 | |
37 public static SLReadPropertyCacheNode create(String propertyName) { | |
38 return new SLUninitializedReadObjectPropertyNode(propertyName); | |
39 } | |
40 | |
41 public abstract Object executeObject(DynamicObject receiver); | |
42 | |
43 public abstract long executeLong(DynamicObject receiver) throws UnexpectedResultException; | |
44 | |
45 protected abstract static class SLReadPropertyCacheChainNode extends SLReadPropertyCacheNode { | |
46 protected final Shape shape; | |
47 @Child protected SLReadPropertyCacheNode next; | |
48 | |
49 public SLReadPropertyCacheChainNode(Shape shape, SLReadPropertyCacheNode next) { | |
50 this.shape = shape; | |
51 this.next = next; | |
52 } | |
53 | |
54 @Override | |
55 public final Object executeObject(DynamicObject receiver) { | |
56 try { | |
57 // if this assumption fails, the object needs to be updated to a valid shape | |
58 shape.getValidAssumption().check(); | |
59 } catch (InvalidAssumptionException e) { | |
60 return this.replace(next).executeObject(receiver); | |
61 } | |
62 | |
63 boolean condition = shape.check(receiver); | |
64 | |
65 if (condition) { | |
66 return executeObjectUnchecked(receiver, condition); | |
67 } else { | |
68 return next.executeObject(receiver); | |
69 } | |
70 } | |
71 | |
72 @Override | |
73 public final long executeLong(DynamicObject receiver) throws UnexpectedResultException { | |
74 try { | |
75 // if this assumption fails, the object needs to be updated to a valid shape | |
76 shape.getValidAssumption().check(); | |
77 } catch (InvalidAssumptionException e) { | |
78 return this.replace(next).executeLong(receiver); | |
79 } | |
80 | |
81 boolean condition = shape.check(receiver); | |
82 | |
83 if (condition) { | |
84 return executeLongUnchecked(receiver, condition); | |
85 } else { | |
86 return next.executeLong(receiver); | |
87 } | |
88 } | |
89 | |
90 protected abstract Object executeObjectUnchecked(DynamicObject receiver, boolean condition); | |
91 | |
92 protected long executeLongUnchecked(DynamicObject receiver, boolean condition) throws UnexpectedResultException { | |
93 return SLTypesGen.SLTYPES.expectLong(executeObjectUnchecked(receiver, condition)); | |
94 } | |
95 } | |
96 | |
97 protected static class SLReadObjectPropertyNode extends SLReadPropertyCacheChainNode { | |
98 private final Location location; | |
99 | |
100 protected SLReadObjectPropertyNode(Shape shape, Location location, SLReadPropertyCacheNode next) { | |
101 super(shape, next); | |
102 this.location = location; | |
103 } | |
104 | |
105 @Override | |
106 protected Object executeObjectUnchecked(DynamicObject receiver, boolean condition) { | |
107 return location.get(receiver, condition); | |
108 } | |
109 } | |
110 | |
111 protected static class SLReadBooleanPropertyNode extends SLReadPropertyCacheChainNode { | |
112 private final BooleanLocation location; | |
113 | |
114 protected SLReadBooleanPropertyNode(Shape shape, BooleanLocation location, SLReadPropertyCacheNode next) { | |
115 super(shape, next); | |
116 this.location = location; | |
117 } | |
118 | |
119 @Override | |
120 protected Object executeObjectUnchecked(DynamicObject receiver, boolean condition) { | |
121 return location.getBoolean(receiver, condition); | |
122 } | |
123 } | |
124 | |
125 protected static class SLReadLongPropertyNode extends SLReadPropertyCacheChainNode { | |
126 private final LongLocation location; | |
127 | |
128 protected SLReadLongPropertyNode(Shape shape, LongLocation location, SLReadPropertyCacheNode next) { | |
129 super(shape, next); | |
130 this.location = location; | |
131 } | |
132 | |
133 @Override | |
134 protected Object executeObjectUnchecked(DynamicObject receiver, boolean condition) { | |
135 return location.getLong(receiver, condition); | |
136 } | |
137 | |
138 @Override | |
139 protected long executeLongUnchecked(DynamicObject receiver, boolean condition) throws UnexpectedResultException { | |
140 return location.getLong(receiver, condition); | |
141 } | |
142 } | |
143 | |
144 protected static class SLReadMissingPropertyNode extends SLReadPropertyCacheChainNode { | |
145 protected SLReadMissingPropertyNode(Shape shape, SLReadPropertyCacheNode next) { | |
146 super(shape, next); | |
147 } | |
148 | |
149 @Override | |
150 protected Object executeObjectUnchecked(DynamicObject receiver, boolean condition) { | |
151 // The property was not found in the object, return null | |
152 return SLNull.SINGLETON; | |
153 } | |
154 } | |
155 | |
156 protected static class SLUninitializedReadObjectPropertyNode extends SLReadPropertyCacheNode { | |
157 protected final String propertyName; | |
158 | |
159 protected SLUninitializedReadObjectPropertyNode(String propertyName) { | |
160 this.propertyName = propertyName; | |
161 } | |
162 | |
163 @Override | |
164 public Object executeObject(DynamicObject receiver) { | |
165 CompilerDirectives.transferToInterpreterAndInvalidate(); | |
166 | |
167 receiver.updateShape(); | |
168 | |
169 Shape shape = receiver.getShape(); | |
170 Property property = shape.getProperty(propertyName); | |
171 | |
172 final SLReadPropertyCacheNode resolvedNode; | |
173 if (property == null) { | |
174 resolvedNode = new SLReadMissingPropertyNode(shape, this); | |
175 } else if (property.getLocation() instanceof LongLocation) { | |
176 resolvedNode = new SLReadLongPropertyNode(shape, (LongLocation) property.getLocation(), this); | |
177 } else if (property.getLocation() instanceof BooleanLocation) { | |
178 resolvedNode = new SLReadBooleanPropertyNode(shape, (BooleanLocation) property.getLocation(), this); | |
179 } else { | |
180 resolvedNode = new SLReadObjectPropertyNode(shape, property.getLocation(), this); | |
181 } | |
182 | |
183 return this.replace(resolvedNode, "resolved '" + propertyName + "'").executeObject(receiver); | |
184 } | |
185 | |
186 @Override | |
187 public long executeLong(DynamicObject receiver) throws UnexpectedResultException { | |
188 return SLTypesGen.SLTYPES.expectLong(executeObject(receiver)); | |
189 } | |
190 } | |
191 } |