Mercurial > projects > ddmd
annotate dmd/Parameter.d @ 130:60bb0fe4563e
dmdfe 2.037 first main iteration
author | Eldar Insafutdinov <e.insafutdinov@gmail.com> |
---|---|
date | Thu, 09 Sep 2010 22:51:44 +0100 |
parents | dmd/Argument.d@1765f3ef917d |
children | 206db751bd4c |
rev | line source |
---|---|
130
60bb0fe4563e
dmdfe 2.037 first main iteration
Eldar Insafutdinov <e.insafutdinov@gmail.com>
parents:
126
diff
changeset
|
1 module dmd.Parameter; |
0 | 2 |
114 | 3 import dmd.common; |
0 | 4 import dmd.Type; |
5 import dmd.Identifier; | |
56 | 6 import dmd.TypeArray; |
7 import dmd.TypeFunction; | |
8 import dmd.TypeDelegate; | |
0 | 9 import dmd.TypeTuple; |
10 import dmd.TY; | |
11 import dmd.Expression; | |
12 import dmd.OutBuffer; | |
13 import dmd.HdrGenState; | |
14 import dmd.ArrayTypes; | |
15 import dmd.StorageClassDeclaration; | |
16 import dmd.Global; | |
17 import dmd.MOD; | |
18 import dmd.CppMangleState; | |
19 import dmd.STC; | |
20 | |
130
60bb0fe4563e
dmdfe 2.037 first main iteration
Eldar Insafutdinov <e.insafutdinov@gmail.com>
parents:
126
diff
changeset
|
21 class Parameter |
0 | 22 { |
23 //enum InOut inout; | |
24 STC storageClass; | |
25 Type type; | |
26 Identifier ident; | |
27 Expression defaultArg; | |
28 | |
29 this(STC storageClass, Type type, Identifier ident, Expression defaultArg) | |
30 { | |
31 this.type = type; | |
32 this.ident = ident; | |
33 this.storageClass = storageClass; | |
34 this.defaultArg = defaultArg; | |
35 } | |
36 | |
130
60bb0fe4563e
dmdfe 2.037 first main iteration
Eldar Insafutdinov <e.insafutdinov@gmail.com>
parents:
126
diff
changeset
|
37 Parameter clone() |
0 | 38 { |
130
60bb0fe4563e
dmdfe 2.037 first main iteration
Eldar Insafutdinov <e.insafutdinov@gmail.com>
parents:
126
diff
changeset
|
39 return new Parameter(storageClass, type, ident, defaultArg); |
0 | 40 } |
41 | |
130
60bb0fe4563e
dmdfe 2.037 first main iteration
Eldar Insafutdinov <e.insafutdinov@gmail.com>
parents:
126
diff
changeset
|
42 Parameter syntaxCopy() |
0 | 43 { |
130
60bb0fe4563e
dmdfe 2.037 first main iteration
Eldar Insafutdinov <e.insafutdinov@gmail.com>
parents:
126
diff
changeset
|
44 return new Parameter(storageClass, type ? type.syntaxCopy() : null, ident, defaultArg ? defaultArg.syntaxCopy() : null); |
0 | 45 } |
46 | |
56 | 47 /**************************************************** |
48 * Determine if parameter is a lazy array of delegates. | |
49 * If so, return the return type of those delegates. | |
50 * If not, return null. | |
51 */ | |
0 | 52 Type isLazyArray() |
53 { | |
56 | 54 // if (inout == Lazy) |
55 { | |
56 Type tb = type.toBasetype(); | |
57 if (tb.ty == Tsarray || tb.ty == Tarray) | |
58 { | |
59 Type tel = (cast(TypeArray)tb).next.toBasetype(); | |
60 if (tel.ty == Tdelegate) | |
61 { | |
62 TypeDelegate td = cast(TypeDelegate)tel; | |
63 TypeFunction tf = cast(TypeFunction)td.next; | |
64 | |
130
60bb0fe4563e
dmdfe 2.037 first main iteration
Eldar Insafutdinov <e.insafutdinov@gmail.com>
parents:
126
diff
changeset
|
65 if (!tf.varargs && Parameter.dim(tf.parameters) == 0) |
56 | 66 { |
67 return tf.next; // return type of delegate | |
68 } | |
69 } | |
70 } | |
71 } | |
72 return null; | |
0 | 73 } |
74 | |
75 void toDecoBuffer(OutBuffer buf) | |
76 { | |
77 if (storageClass & STC.STCscope) | |
78 buf.writeByte('M'); | |
79 switch (storageClass & (STC.STCin | STC.STCout | STC.STCref | STC.STClazy)) | |
80 { | |
81 case STC.STCundefined: | |
82 case STC.STCin: | |
83 break; | |
84 case STC.STCout: | |
85 buf.writeByte('J'); | |
86 break; | |
87 case STC.STCref: | |
88 buf.writeByte('K'); | |
89 break; | |
90 case STC.STClazy: | |
91 buf.writeByte('L'); | |
92 break; | |
93 } | |
94 static if (false) { | |
95 int mod = 0x100; | |
96 if (type.toBasetype().ty == TY.Tclass) | |
97 mod = 0; | |
98 type.toDecoBuffer(buf, mod); | |
99 } else { | |
100 //type.toHeadMutable().toDecoBuffer(buf, 0); | |
101 type.toDecoBuffer(buf, 0); | |
102 } | |
103 } | |
104 | |
130
60bb0fe4563e
dmdfe 2.037 first main iteration
Eldar Insafutdinov <e.insafutdinov@gmail.com>
parents:
126
diff
changeset
|
105 static Parameters arraySyntaxCopy(Parameters args) |
0 | 106 { |
126
1765f3ef917d
ClassDeclarations, Arguments -> Vector
Eldar Insafutdinov <e.insafutdinov@gmail.com>
parents:
114
diff
changeset
|
107 typeof(return) a = null; |
0 | 108 |
109 if (args) | |
110 { | |
130
60bb0fe4563e
dmdfe 2.037 first main iteration
Eldar Insafutdinov <e.insafutdinov@gmail.com>
parents:
126
diff
changeset
|
111 a = new Parameters(); |
0 | 112 a.setDim(args.dim); |
113 | |
114 for (size_t i = 0; i < a.dim; i++) | |
115 { | |
126
1765f3ef917d
ClassDeclarations, Arguments -> Vector
Eldar Insafutdinov <e.insafutdinov@gmail.com>
parents:
114
diff
changeset
|
116 auto arg = args[i]; |
0 | 117 |
118 arg = arg.syntaxCopy(); | |
126
1765f3ef917d
ClassDeclarations, Arguments -> Vector
Eldar Insafutdinov <e.insafutdinov@gmail.com>
parents:
114
diff
changeset
|
119 a[i] = arg; |
0 | 120 } |
121 } | |
122 | |
123 return a; | |
124 } | |
125 | |
130
60bb0fe4563e
dmdfe 2.037 first main iteration
Eldar Insafutdinov <e.insafutdinov@gmail.com>
parents:
126
diff
changeset
|
126 static string argsTypesToChars(Parameters args, int varargs) |
0 | 127 { |
128 scope OutBuffer buf = new OutBuffer(); | |
129 | |
130 static if (true) { | |
131 HdrGenState hgs; | |
132 argsToCBuffer(buf, &hgs, args, varargs); | |
133 } else { | |
134 buf.writeByte('('); | |
135 if (args) | |
136 { | |
16
5c9b78899f5d
Implemented methods for Tuples, fixed some linking issues.
Robert Clipsham <robert@octarineparrot.com>
parents:
0
diff
changeset
|
137 OutBuffer argbuf = new OutBuffer(); |
0 | 138 HdrGenState hgs; |
139 | |
140 for (int i = 0; i < args.dim; i++) | |
141 { | |
142 if (i) | |
143 buf.writeByte(','); | |
130
60bb0fe4563e
dmdfe 2.037 first main iteration
Eldar Insafutdinov <e.insafutdinov@gmail.com>
parents:
126
diff
changeset
|
144 auto arg = cast(Parameter)args.data[i]; |
0 | 145 argbuf.reset(); |
146 arg.type.toCBuffer2(&argbuf, &hgs, 0); | |
147 buf.write(&argbuf); | |
148 } | |
149 if (varargs) | |
150 { | |
151 if (i && varargs == 1) | |
152 buf.writeByte(','); | |
153 buf.writestring("..."); | |
154 } | |
155 } | |
156 buf.writeByte(')'); | |
157 } | |
158 return buf.toChars(); | |
159 } | |
160 | |
130
60bb0fe4563e
dmdfe 2.037 first main iteration
Eldar Insafutdinov <e.insafutdinov@gmail.com>
parents:
126
diff
changeset
|
161 static void argsCppMangle(OutBuffer buf, CppMangleState* cms, Parameters arguments, int varargs) |
0 | 162 { |
163 assert(false); | |
164 } | |
165 | |
130
60bb0fe4563e
dmdfe 2.037 first main iteration
Eldar Insafutdinov <e.insafutdinov@gmail.com>
parents:
126
diff
changeset
|
166 static void argsToCBuffer(OutBuffer buf, HdrGenState* hgs, Parameters arguments, int varargs) |
0 | 167 { |
168 buf.writeByte('('); | |
169 if (arguments) | |
170 { | |
171 int i; | |
172 scope OutBuffer argbuf = new OutBuffer(); | |
173 | |
174 for (i = 0; i < arguments.dim; i++) | |
175 { | |
176 if (i) | |
177 buf.writestring(", "); | |
126
1765f3ef917d
ClassDeclarations, Arguments -> Vector
Eldar Insafutdinov <e.insafutdinov@gmail.com>
parents:
114
diff
changeset
|
178 auto arg = arguments[i]; |
0 | 179 |
180 if (arg.storageClass & STCout) | |
181 buf.writestring("out "); | |
182 else if (arg.storageClass & STCref) | |
183 buf.writestring((global.params.Dversion == 1) ? "inout " : "ref "); | |
184 else if (arg.storageClass & STCin) | |
185 buf.writestring("in "); | |
186 else if (arg.storageClass & STClazy) | |
187 buf.writestring("lazy "); | |
188 else if (arg.storageClass & STCalias) | |
189 buf.writestring("alias "); | |
190 else if (arg.storageClass & STCauto) | |
191 buf.writestring("auto "); | |
192 | |
193 uint stc = arg.storageClass; | |
194 if (arg.type && arg.type.mod & MODshared) | |
195 stc &= ~STCshared; | |
196 | |
197 StorageClassDeclaration.stcToCBuffer(buf, stc & (STCconst | STCimmutable | STCshared | STCscope)); | |
198 | |
199 argbuf.reset(); | |
200 if (arg.storageClass & STCalias) | |
201 { | |
202 if (arg.ident) | |
203 argbuf.writestring(arg.ident.toChars()); | |
204 } | |
205 else | |
206 arg.type.toCBuffer(argbuf, arg.ident, hgs); | |
207 if (arg.defaultArg) | |
208 { | |
209 argbuf.writestring(" = "); | |
210 arg.defaultArg.toCBuffer(argbuf, hgs); | |
211 } | |
212 buf.write(argbuf); | |
213 } | |
214 if (varargs) | |
215 { | |
216 if (i && varargs == 1) | |
217 buf.writeByte(','); | |
218 buf.writestring("..."); | |
219 } | |
220 } | |
221 buf.writeByte(')'); | |
222 } | |
223 | |
130
60bb0fe4563e
dmdfe 2.037 first main iteration
Eldar Insafutdinov <e.insafutdinov@gmail.com>
parents:
126
diff
changeset
|
224 static void argsToDecoBuffer(OutBuffer buf, Parameters arguments) |
0 | 225 { |
130
60bb0fe4563e
dmdfe 2.037 first main iteration
Eldar Insafutdinov <e.insafutdinov@gmail.com>
parents:
126
diff
changeset
|
226 //printf("Parameter::argsToDecoBuffer()\n"); |
0 | 227 |
228 // Write argument types | |
229 if (arguments) | |
230 { | |
130
60bb0fe4563e
dmdfe 2.037 first main iteration
Eldar Insafutdinov <e.insafutdinov@gmail.com>
parents:
126
diff
changeset
|
231 size_t dim = Parameter.dim(arguments); |
0 | 232 for (size_t i = 0; i < dim; i++) |
233 { | |
130
60bb0fe4563e
dmdfe 2.037 first main iteration
Eldar Insafutdinov <e.insafutdinov@gmail.com>
parents:
126
diff
changeset
|
234 auto arg = Parameter.getNth(arguments, i); |
0 | 235 arg.toDecoBuffer(buf); |
236 } | |
237 } | |
238 } | |
239 | |
130
60bb0fe4563e
dmdfe 2.037 first main iteration
Eldar Insafutdinov <e.insafutdinov@gmail.com>
parents:
126
diff
changeset
|
240 static int isTPL(Parameters arguments) |
0 | 241 { |
242 assert(false); | |
243 } | |
244 | |
245 /*************************************** | |
246 * Determine number of arguments, folding in tuples. | |
247 */ | |
130
60bb0fe4563e
dmdfe 2.037 first main iteration
Eldar Insafutdinov <e.insafutdinov@gmail.com>
parents:
126
diff
changeset
|
248 static size_t dim(Parameters args) |
0 | 249 { |
250 size_t n = 0; | |
251 if (args) | |
252 { | |
126
1765f3ef917d
ClassDeclarations, Arguments -> Vector
Eldar Insafutdinov <e.insafutdinov@gmail.com>
parents:
114
diff
changeset
|
253 foreach (arg; args) |
0 | 254 { |
255 Type t = arg.type.toBasetype(); | |
256 | |
257 if (t.ty == TY.Ttuple) | |
258 { | |
126
1765f3ef917d
ClassDeclarations, Arguments -> Vector
Eldar Insafutdinov <e.insafutdinov@gmail.com>
parents:
114
diff
changeset
|
259 auto tu = cast(TypeTuple)t; |
0 | 260 n += dim(tu.arguments); |
261 } | |
262 else | |
263 n++; | |
264 } | |
265 } | |
266 return n; | |
267 } | |
268 | |
269 /*************************************** | |
130
60bb0fe4563e
dmdfe 2.037 first main iteration
Eldar Insafutdinov <e.insafutdinov@gmail.com>
parents:
126
diff
changeset
|
270 * Get nth Parameter, folding in tuples. |
0 | 271 * Returns: |
130
60bb0fe4563e
dmdfe 2.037 first main iteration
Eldar Insafutdinov <e.insafutdinov@gmail.com>
parents:
126
diff
changeset
|
272 * Parameter nth Parameter |
0 | 273 * null not found, *pn gets incremented by the number |
130
60bb0fe4563e
dmdfe 2.037 first main iteration
Eldar Insafutdinov <e.insafutdinov@gmail.com>
parents:
126
diff
changeset
|
274 * of Parameters |
0 | 275 */ |
130
60bb0fe4563e
dmdfe 2.037 first main iteration
Eldar Insafutdinov <e.insafutdinov@gmail.com>
parents:
126
diff
changeset
|
276 static Parameter getNth(Parameters args, size_t nth, size_t* pn = null) |
0 | 277 { |
278 if (!args) | |
279 return null; | |
280 | |
281 size_t n = 0; | |
126
1765f3ef917d
ClassDeclarations, Arguments -> Vector
Eldar Insafutdinov <e.insafutdinov@gmail.com>
parents:
114
diff
changeset
|
282 foreach (arg; args) |
0 | 283 { |
284 Type t = arg.type.toBasetype(); | |
285 | |
286 if (t.ty == TY.Ttuple) | |
287 { TypeTuple tu = cast(TypeTuple)t; | |
288 arg = getNth(tu.arguments, nth - n, &n); | |
289 if (arg) | |
290 return arg; | |
291 } | |
292 else if (n == nth) | |
293 return arg; | |
294 else | |
295 n++; | |
296 } | |
297 | |
298 if (pn) | |
299 *pn += n; | |
300 | |
301 return null; | |
302 } | |
16
5c9b78899f5d
Implemented methods for Tuples, fixed some linking issues.
Robert Clipsham <robert@octarineparrot.com>
parents:
0
diff
changeset
|
303 } |