55
55
import com .oracle .graal .python .builtins .modules .cext .PythonCextBuiltins .CApiUnaryBuiltinNode ;
56
56
import com .oracle .graal .python .builtins .modules .cext .PythonCextBuiltins .PromoteBorrowedValue ;
57
57
import com .oracle .graal .python .builtins .objects .PNone ;
58
+ import com .oracle .graal .python .builtins .objects .cext .PythonAbstractNativeObject ;
58
59
import com .oracle .graal .python .builtins .objects .common .SequenceStorageNodes ;
60
+ import com .oracle .graal .python .builtins .objects .common .SequenceStorageNodes .GetItemNode ;
59
61
import com .oracle .graal .python .builtins .objects .common .SequenceStorageNodes .GetItemScalarNode ;
60
62
import com .oracle .graal .python .builtins .objects .common .SequenceStorageNodes .ListGeneralizationNode ;
63
+ import com .oracle .graal .python .builtins .objects .common .SequenceStorageNodes .SetItemNode ;
61
64
import com .oracle .graal .python .builtins .objects .common .SequenceStorageNodes .SetItemScalarNode ;
62
65
import com .oracle .graal .python .builtins .objects .tuple .PTuple ;
63
- import com .oracle .graal .python .builtins .objects .tuple .TupleBuiltins .GetItemNode ;
64
66
import com .oracle .graal .python .lib .PySliceNew ;
67
+ import com .oracle .graal .python .lib .PyTupleSizeNode ;
65
68
import com .oracle .graal .python .nodes .ErrorMessages ;
69
+ import com .oracle .graal .python .nodes .builtins .TupleNodes .GetNativeTupleStorage ;
66
70
import com .oracle .graal .python .runtime .sequence .storage .SequenceStorage ;
67
71
import com .oracle .truffle .api .dsl .Cached ;
72
+ import com .oracle .truffle .api .dsl .Cached .Shared ;
68
73
import com .oracle .truffle .api .dsl .Fallback ;
69
74
import com .oracle .truffle .api .dsl .Specialization ;
70
75
import com .oracle .truffle .api .profiles .ConditionProfile ;
@@ -83,16 +88,41 @@ PTuple doGeneric(long size) {
83
88
@ CApiBuiltin (ret = Int , args = {PyObject , Py_ssize_t , PyObjectTransfer }, call = Direct )
84
89
public abstract static class PyTuple_SetItem extends CApiTernaryBuiltinNode {
85
90
@ Specialization
86
- static int doManaged (PTuple tuple , Object position , Object element ,
87
- @ Cached ("createForList ()" ) SequenceStorageNodes .SetItemNode setItemNode ,
91
+ int doManaged (PTuple tuple , long index , Object element ,
92
+ @ Shared ( "setItem" ) @ Cached ("createSetItem ()" ) SequenceStorageNodes .SetItemNode setItemNode ,
88
93
@ Cached ConditionProfile generalizedProfile ) {
89
- setItemNode .execute (null , tuple .getSequenceStorage (), position , element );
90
- SequenceStorage newStorage = setItemNode .execute (null , tuple .getSequenceStorage (), position , element );
94
+ SequenceStorage newStorage = setItem (tuple .getSequenceStorage (), index , element , setItemNode );
91
95
if (generalizedProfile .profile (tuple .getSequenceStorage () != newStorage )) {
92
96
tuple .setSequenceStorage (newStorage );
93
97
}
94
98
return 0 ;
95
99
}
100
+
101
+ @ Specialization
102
+ int doNative (PythonAbstractNativeObject tuple , long index , Object element ,
103
+ @ Cached GetNativeTupleStorage asNativeStorage ,
104
+ @ Shared ("setItem" ) @ Cached ("createSetItem()" ) SequenceStorageNodes .SetItemNode setItemNode ) {
105
+ setItem (asNativeStorage .execute (tuple ), index , element , setItemNode );
106
+ return 0 ;
107
+ }
108
+
109
+ @ Fallback
110
+ @ SuppressWarnings ("unused" )
111
+ Object fallback (Object tuple , Object index , Object element ) {
112
+ throw raiseFallback (tuple , PythonBuiltinClassType .PTuple );
113
+ }
114
+
115
+ private SequenceStorage setItem (SequenceStorage sequenceStorage , long index , Object element , SetItemNode setItemNode ) {
116
+ // we must do a bounds-check but we must not normalize the index
117
+ if (index < 0 || index >= sequenceStorage .length ()) {
118
+ throw raise (IndexError , ErrorMessages .TUPLE_OUT_OF_BOUNDS );
119
+ }
120
+ return setItemNode .execute (null , sequenceStorage , (int ) index , element );
121
+ }
122
+
123
+ protected static SetItemNode createSetItem () {
124
+ return SetItemNode .create (null , ListGeneralizationNode ::create );
125
+ }
96
126
}
97
127
98
128
@ CApiBuiltin (ret = PyObjectBorrowed , args = {PyObject , Py_ssize_t }, call = Direct )
@@ -102,21 +132,35 @@ public abstract static class PyTuple_GetItem extends CApiBinaryBuiltinNode {
102
132
103
133
@ Specialization
104
134
Object doPTuple (PTuple tuple , long key ,
105
- @ Cached PromoteBorrowedValue promoteNode ,
135
+ @ Shared ( "promote" ) @ Cached PromoteBorrowedValue promoteNode ,
106
136
@ Cached ListGeneralizationNode generalizationNode ,
107
- @ Cached SetItemScalarNode setItemNode ,
108
- @ Cached GetItemScalarNode getItemNode ) {
137
+ @ Shared ( "setItem" ) @ Cached SetItemScalarNode setItemNode ,
138
+ @ Shared ( "getItem" ) @ Cached GetItemScalarNode getItemNode ) {
109
139
SequenceStorage sequenceStorage = tuple .getSequenceStorage ();
110
- // we must do a bounds-check but we must not normalize the index
111
- if (key < 0 || key >= sequenceStorage .length ()) {
112
- throw raise (IndexError , ErrorMessages .TUPLE_OUT_OF_BOUNDS );
113
- }
114
- Object result = getItemNode .execute (sequenceStorage , (int ) key );
140
+ int index = checkIndex (key , sequenceStorage );
141
+ Object result = getItemNode .execute (sequenceStorage , index );
115
142
Object promotedValue = promoteNode .execute (result );
116
143
if (promotedValue != null ) {
117
144
sequenceStorage = generalizationNode .execute (sequenceStorage , promotedValue );
118
145
tuple .setSequenceStorage (sequenceStorage );
119
- setItemNode .execute (sequenceStorage , (int ) key , promotedValue );
146
+ setItemNode .execute (sequenceStorage , index , promotedValue );
147
+ return promotedValue ;
148
+ }
149
+ return result ;
150
+ }
151
+
152
+ @ Specialization
153
+ Object doNative (PythonAbstractNativeObject tuple , long key ,
154
+ @ Cached GetNativeTupleStorage asNativeStorage ,
155
+ @ Shared ("promote" ) @ Cached PromoteBorrowedValue promoteNode ,
156
+ @ Shared ("setItem" ) @ Cached SetItemScalarNode setItemNode ,
157
+ @ Shared ("getItem" ) @ Cached GetItemScalarNode getItemNode ) {
158
+ SequenceStorage sequenceStorage = asNativeStorage .execute (tuple );
159
+ int index = checkIndex (key , sequenceStorage );
160
+ Object result = getItemNode .execute (sequenceStorage , index );
161
+ Object promotedValue = promoteNode .execute (result );
162
+ if (promotedValue != null ) {
163
+ setItemNode .execute (sequenceStorage , index , promotedValue );
120
164
return promotedValue ;
121
165
}
122
166
return result ;
@@ -126,13 +170,21 @@ Object doPTuple(PTuple tuple, long key,
126
170
Object fallback (Object tuple , @ SuppressWarnings ("unused" ) Object pos ) {
127
171
throw raiseFallback (tuple , PythonBuiltinClassType .PTuple );
128
172
}
173
+
174
+ private int checkIndex (long key , SequenceStorage sequenceStorage ) {
175
+ // we must do a bounds-check but we must not normalize the index
176
+ if (key < 0 || key >= sequenceStorage .length ()) {
177
+ throw raise (IndexError , ErrorMessages .TUPLE_OUT_OF_BOUNDS );
178
+ }
179
+ return (int ) key ;
180
+ }
129
181
}
130
182
131
183
@ CApiBuiltin (ret = Py_ssize_t , args = {PyObject }, call = Direct )
132
184
public abstract static class PyTuple_Size extends CApiUnaryBuiltinNode {
133
185
@ Specialization
134
186
public static int size (Object tuple ,
135
- @ Cached com . oracle . graal . python . lib . PyTupleSizeNode pyTupleSizeNode ) {
187
+ @ Cached PyTupleSizeNode pyTupleSizeNode ) {
136
188
return pyTupleSizeNode .execute (tuple );
137
189
}
138
190
}
@@ -141,15 +193,27 @@ public static int size(Object tuple,
141
193
abstract static class PyTuple_GetSlice extends CApiTernaryBuiltinNode {
142
194
@ Specialization
143
195
Object getSlice (PTuple tuple , Object iLow , Object iHigh ,
144
- @ Cached GetItemNode getItemNode ,
145
- @ Cached PySliceNew sliceNode ) {
146
- return getItemNode .execute (null , tuple , sliceNode .execute (iLow , iHigh , PNone .NONE ));
196
+ @ Shared ("getItem" ) @ Cached ("createForTuple()" ) SequenceStorageNodes .GetItemNode getItemNode ,
197
+ @ Shared ("newSlice" ) @ Cached PySliceNew sliceNode ) {
198
+ return doGetSlice (tuple .getSequenceStorage (), iLow , iHigh , getItemNode , sliceNode );
199
+ }
200
+
201
+ @ Specialization
202
+ Object doNative (PythonAbstractNativeObject tuple , Object iLow , Object iHigh ,
203
+ @ Shared ("getItem" ) @ Cached ("createForTuple()" ) SequenceStorageNodes .GetItemNode getItemNode ,
204
+ @ Shared ("newSlice" ) @ Cached PySliceNew sliceNode ,
205
+ @ Cached GetNativeTupleStorage asNativeStorage ) {
206
+ return doGetSlice (asNativeStorage .execute (tuple ), iLow , iHigh , getItemNode , sliceNode );
147
207
}
148
208
149
209
@ SuppressWarnings ("unused" )
150
210
@ Fallback
151
211
Object fallback (Object tuple , Object iLow , Object iHigh ) {
152
212
throw raiseFallback (tuple , PythonBuiltinClassType .PTuple );
153
213
}
214
+
215
+ private static Object doGetSlice (SequenceStorage storage , Object iLow , Object iHigh , GetItemNode getItemNode , PySliceNew sliceNode ) {
216
+ return getItemNode .execute (null , storage , sliceNode .execute (iLow , iHigh , PNone .NONE ));
217
+ }
154
218
}
155
219
}
0 commit comments