annotate dmd/expression/Index.d @ 0:10317f0c89a5

Initial commit
author korDen
date Sat, 24 Oct 2009 08:42:06 +0400
parents
children 39648eb578f6
Ignore whitespace changes - Everywhere: Within whitespace: At end of lines:
rev   line source
0
10317f0c89a5 Initial commit
korDen
parents:
diff changeset
1 module dmd.expression.Index;
10317f0c89a5 Initial commit
korDen
parents:
diff changeset
2
10317f0c89a5 Initial commit
korDen
parents:
diff changeset
3 import dmd.Type;
10317f0c89a5 Initial commit
korDen
parents:
diff changeset
4 import dmd.Loc;
10317f0c89a5 Initial commit
korDen
parents:
diff changeset
5 import dmd.StringExp;
10317f0c89a5 Initial commit
korDen
parents:
diff changeset
6 import dmd.TOK;
10317f0c89a5 Initial commit
korDen
parents:
diff changeset
7 import dmd.Expression;
10317f0c89a5 Initial commit
korDen
parents:
diff changeset
8 import dmd.GlobalExpressions;
10317f0c89a5 Initial commit
korDen
parents:
diff changeset
9 import dmd.IntegerExp;
10317f0c89a5 Initial commit
korDen
parents:
diff changeset
10 import dmd.TY;
10317f0c89a5 Initial commit
korDen
parents:
diff changeset
11 import dmd.TypeSArray;
10317f0c89a5 Initial commit
korDen
parents:
diff changeset
12 import dmd.ArrayLiteralExp;
10317f0c89a5 Initial commit
korDen
parents:
diff changeset
13 import dmd.AssocArrayLiteralExp;
10317f0c89a5 Initial commit
korDen
parents:
diff changeset
14
10317f0c89a5 Initial commit
korDen
parents:
diff changeset
15 import dmd.expression.Equal;
10317f0c89a5 Initial commit
korDen
parents:
diff changeset
16
10317f0c89a5 Initial commit
korDen
parents:
diff changeset
17 /* Also return EXP_CANT_INTERPRET if this fails
10317f0c89a5 Initial commit
korDen
parents:
diff changeset
18 */
10317f0c89a5 Initial commit
korDen
parents:
diff changeset
19 Expression Index(Type type, Expression e1, Expression e2)
10317f0c89a5 Initial commit
korDen
parents:
diff changeset
20 {
10317f0c89a5 Initial commit
korDen
parents:
diff changeset
21 Expression e = EXP_CANT_INTERPRET;
10317f0c89a5 Initial commit
korDen
parents:
diff changeset
22 Loc loc = e1.loc;
10317f0c89a5 Initial commit
korDen
parents:
diff changeset
23
10317f0c89a5 Initial commit
korDen
parents:
diff changeset
24 //printf("Index(e1 = %s, e2 = %s)\n", e1.toChars(), e2.toChars());
10317f0c89a5 Initial commit
korDen
parents:
diff changeset
25 assert(e1.type);
10317f0c89a5 Initial commit
korDen
parents:
diff changeset
26 if (e1.op == TOKstring && e2.op == TOKint64)
10317f0c89a5 Initial commit
korDen
parents:
diff changeset
27 {
10317f0c89a5 Initial commit
korDen
parents:
diff changeset
28 StringExp es1 = cast(StringExp)e1;
10317f0c89a5 Initial commit
korDen
parents:
diff changeset
29 ulong i = e2.toInteger();
10317f0c89a5 Initial commit
korDen
parents:
diff changeset
30
10317f0c89a5 Initial commit
korDen
parents:
diff changeset
31 if (i >= es1.len)
10317f0c89a5 Initial commit
korDen
parents:
diff changeset
32 e1.error("string index %ju is out of bounds [0 .. %zu]", i, es1.len);
10317f0c89a5 Initial commit
korDen
parents:
diff changeset
33 else
10317f0c89a5 Initial commit
korDen
parents:
diff changeset
34 {
10317f0c89a5 Initial commit
korDen
parents:
diff changeset
35 uint value = es1.charAt(cast(uint)i);
10317f0c89a5 Initial commit
korDen
parents:
diff changeset
36 e = new IntegerExp(loc, value, type);
10317f0c89a5 Initial commit
korDen
parents:
diff changeset
37 }
10317f0c89a5 Initial commit
korDen
parents:
diff changeset
38 }
10317f0c89a5 Initial commit
korDen
parents:
diff changeset
39 else if (e1.type.toBasetype().ty == Tsarray && e2.op == TOKint64)
10317f0c89a5 Initial commit
korDen
parents:
diff changeset
40 {
10317f0c89a5 Initial commit
korDen
parents:
diff changeset
41 TypeSArray tsa = cast(TypeSArray)e1.type.toBasetype();
10317f0c89a5 Initial commit
korDen
parents:
diff changeset
42 ulong length = tsa.dim.toInteger();
10317f0c89a5 Initial commit
korDen
parents:
diff changeset
43 ulong i = e2.toInteger();
10317f0c89a5 Initial commit
korDen
parents:
diff changeset
44
10317f0c89a5 Initial commit
korDen
parents:
diff changeset
45 if (i >= length)
10317f0c89a5 Initial commit
korDen
parents:
diff changeset
46 {
10317f0c89a5 Initial commit
korDen
parents:
diff changeset
47 e2.error("array index %ju is out of bounds %s[0 .. %ju]", i, e1.toChars(), length);
10317f0c89a5 Initial commit
korDen
parents:
diff changeset
48 }
10317f0c89a5 Initial commit
korDen
parents:
diff changeset
49 else if (e1.op == TOKarrayliteral && !e1.checkSideEffect(2))
10317f0c89a5 Initial commit
korDen
parents:
diff changeset
50 {
10317f0c89a5 Initial commit
korDen
parents:
diff changeset
51 ArrayLiteralExp ale = cast(ArrayLiteralExp)e1;
10317f0c89a5 Initial commit
korDen
parents:
diff changeset
52 e = cast(Expression)ale.elements.data[cast(uint)i];
10317f0c89a5 Initial commit
korDen
parents:
diff changeset
53 e.type = type;
10317f0c89a5 Initial commit
korDen
parents:
diff changeset
54 }
10317f0c89a5 Initial commit
korDen
parents:
diff changeset
55 }
10317f0c89a5 Initial commit
korDen
parents:
diff changeset
56 else if (e1.type.toBasetype().ty == Tarray && e2.op == TOKint64)
10317f0c89a5 Initial commit
korDen
parents:
diff changeset
57 {
10317f0c89a5 Initial commit
korDen
parents:
diff changeset
58 ulong i = e2.toInteger();
10317f0c89a5 Initial commit
korDen
parents:
diff changeset
59
10317f0c89a5 Initial commit
korDen
parents:
diff changeset
60 if (e1.op == TOKarrayliteral && !e1.checkSideEffect(2))
10317f0c89a5 Initial commit
korDen
parents:
diff changeset
61 {
10317f0c89a5 Initial commit
korDen
parents:
diff changeset
62 ArrayLiteralExp ale = cast(ArrayLiteralExp)e1;
10317f0c89a5 Initial commit
korDen
parents:
diff changeset
63 if (i >= ale.elements.dim)
10317f0c89a5 Initial commit
korDen
parents:
diff changeset
64 {
10317f0c89a5 Initial commit
korDen
parents:
diff changeset
65 e2.error("array index %ju is out of bounds %s[0 .. %u]", i, e1.toChars(), ale.elements.dim);
10317f0c89a5 Initial commit
korDen
parents:
diff changeset
66 }
10317f0c89a5 Initial commit
korDen
parents:
diff changeset
67 else
10317f0c89a5 Initial commit
korDen
parents:
diff changeset
68 {
10317f0c89a5 Initial commit
korDen
parents:
diff changeset
69 e = cast(Expression)ale.elements.data[cast(uint)i];
10317f0c89a5 Initial commit
korDen
parents:
diff changeset
70 e.type = type;
10317f0c89a5 Initial commit
korDen
parents:
diff changeset
71 }
10317f0c89a5 Initial commit
korDen
parents:
diff changeset
72 }
10317f0c89a5 Initial commit
korDen
parents:
diff changeset
73 }
10317f0c89a5 Initial commit
korDen
parents:
diff changeset
74 else if (e1.op == TOKassocarrayliteral && !e1.checkSideEffect(2))
10317f0c89a5 Initial commit
korDen
parents:
diff changeset
75 {
10317f0c89a5 Initial commit
korDen
parents:
diff changeset
76 AssocArrayLiteralExp ae = cast(AssocArrayLiteralExp)e1;
10317f0c89a5 Initial commit
korDen
parents:
diff changeset
77 /* Search the keys backwards, in case there are duplicate keys
10317f0c89a5 Initial commit
korDen
parents:
diff changeset
78 */
10317f0c89a5 Initial commit
korDen
parents:
diff changeset
79 for (size_t i = ae.keys.dim; i;)
10317f0c89a5 Initial commit
korDen
parents:
diff changeset
80 {
10317f0c89a5 Initial commit
korDen
parents:
diff changeset
81 i--;
10317f0c89a5 Initial commit
korDen
parents:
diff changeset
82 Expression ekey = cast(Expression)ae.keys.data[i];
10317f0c89a5 Initial commit
korDen
parents:
diff changeset
83 Expression ex = Equal(TOKequal, Type.tbool, ekey, e2);
10317f0c89a5 Initial commit
korDen
parents:
diff changeset
84 if (ex is EXP_CANT_INTERPRET)
10317f0c89a5 Initial commit
korDen
parents:
diff changeset
85 return ex;
10317f0c89a5 Initial commit
korDen
parents:
diff changeset
86 if (ex.isBool(true))
10317f0c89a5 Initial commit
korDen
parents:
diff changeset
87 {
10317f0c89a5 Initial commit
korDen
parents:
diff changeset
88 e = cast(Expression)ae.values.data[i];
10317f0c89a5 Initial commit
korDen
parents:
diff changeset
89 e.type = type;
10317f0c89a5 Initial commit
korDen
parents:
diff changeset
90 break;
10317f0c89a5 Initial commit
korDen
parents:
diff changeset
91 }
10317f0c89a5 Initial commit
korDen
parents:
diff changeset
92 }
10317f0c89a5 Initial commit
korDen
parents:
diff changeset
93 }
10317f0c89a5 Initial commit
korDen
parents:
diff changeset
94
10317f0c89a5 Initial commit
korDen
parents:
diff changeset
95 return e;
10317f0c89a5 Initial commit
korDen
parents:
diff changeset
96 }